SisMaker 5 роки тому
джерело
коміт
87135e2642
7 змінених файлів з 468 додано та 12 видалено
  1. +1
    -0
      include/erlArango.hrl
  2. +10
    -10
      src/arangoApi/agCollections.erl
  3. +2
    -2
      src/arangoApi/agDbMgr.erl
  4. +336
    -0
      src/arangoApi/agDocuments.erl
  5. +26
    -0
      src/arangoApi/agEdges.erl
  6. +82
    -0
      src/arangoApi/agGeneralGraphs.erl
  7. +11
    -0
      src/httpCli/agMiscUtils.erl

+ 1
- 0
include/erlArango.hrl Переглянути файл

@ -5,4 +5,5 @@
-define(Put, <<"PUT">>).
-define(Post, <<"POST">>).
-define(Head, <<"HEAD">>).
-define(Patch, <<"PATCH">>).
-define(Delete, <<"DELETE">>).

+ 10
- 10
src/arangoApi/agCollections.erl Переглянути файл

@ -73,12 +73,12 @@
%
% 400HTTP 400
% 404HTTP 404
newColl(PoolNameOrSocket, Args) ->
BodyStr = jiffy:encode(Args),
newColl(PoolNameOrSocket, MapData) ->
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, <<"/_api/collection">>, [], BodyStr).
newColl(PoolNameOrSocket, Args, WaitForSyncReplication, ForceReplicationFactor) ->
BodyStr = jiffy:encode(Args),
newColl(PoolNameOrSocket, MapData, WaitForSyncReplication, ForceReplicationFactor) ->
BodyStr = jiffy:encode(MapData),
Path = <<"/_api/collection?waitForSyncReplication=", (erlang:integer_to_binary(WaitForSyncReplication))/binary, "&forceReplicationFactor=", (erlang:integer_to_binary(ForceReplicationFactor))/binary>>,
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).
@ -166,11 +166,11 @@ collFigures(PoolNameOrSocket, CollName) ->
% JSON文档
% shardId属性的JSON对象ID
%
% eg: args = #{'_key' => testkey, value => 23}
% eg: MapData = #{'_key' => testkey, value => 23}
collResponsibleShard(PoolNameOrSocket, CollName, Args) ->
collResponsibleShard(PoolNameOrSocket, CollName, MapData) ->
Path = <<"/_api/collection/", CollName/binary, "/responsibleShard">>,
BodyStr = jiffy:encode(Args),
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Get, Path, [], BodyStr).
% ID
@ -300,7 +300,7 @@ collLoadIndexesIntoMemory(PoolNameOrSocket, CollName) ->
Path = <<"/_api/collection/", CollName/binary, "/loadIndexesIntoMemory">>,
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], undefined).
%
%
% PUT /_api/collection/{collection-name}/properties
%
% collection-name
@ -324,9 +324,9 @@ collLoadIndexesIntoMemory(PoolNameOrSocket, CollName) ->
% allowUserKeystrue_key属性中提供自己的键值 false_key属性中提供自己的密钥值被视为错误
% waitForSyncjournalSize和name之外使
collChangeProperties(PoolNameOrSocket, CollName, Args) ->
collChangeProperties(PoolNameOrSocket, CollName, MapData) ->
Path = <<"/_api/collection/", CollName/binary, "/properties">>,
BodyStr = jiffy:encode(Args),
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], BodyStr).
%

+ 2
- 2
src/arangoApi/agDbMgr.erl Переглянути файл

@ -40,8 +40,8 @@ curDbList(PoolNameOrSocket) ->
% activetruefalse
% extraJSON对象Extra中包含的数据 ArangoDB不会进一步解释
newDb(PoolNameOrSocket, Args) ->
BodyStr = jiffy:encode(Args),
newDb(PoolNameOrSocket, MapData) ->
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, <<"/_api/database">>, [], BodyStr, true).
%%

+ 336
- 0
src/arangoApi/agDocuments.erl Переглянути файл

@ -50,4 +50,340 @@ getDocHead(PoolNameOrSocket, CollName, Key, Headers) ->
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary>>,
agHttpCli:callAgency(PoolNameOrSocket, ?Head, Path, Headers, undefined).
%
% POST /_api/document/{collection}
%
%
%
% ArangoDB版本<3.0URL路径为/ _api / documentURL路径中指定集合
% waitForSync
% returnNew new属性下返回完整的新文档
% returnOld old属性下返回完整的旧文档使
% true
% true_key的文档
% json
% JSON表示形式
% _key的文档_key_key
% _id和_rev属性被忽略URL部分或查询参数集合分别计数
% Location标头将包含新创建的文档的路径Etag的头字段包含了文档的修订
% silent未设置为trueJSON对象
% _id包含新创建的文档的文档标识符
% _key包含文档密钥
% _rev包含文档修订版
% collection参数waitForSync为false
% 使waitForSync标志waitForSync也可用于强制将文档创建操作同步到磁盘waitForSync查询参数可用于强制执行此特定操作的同步使waitForSync参数设置为true waitForSync参数或将其设置为falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% returnNew为truenew属性下返回完整的新文档
%
% 201waitForSync为true
% 202waitForSync为false
% 400JSON表示形式
% 404collection指定的collection未知
% 409409
newDocument(PoolNameOrSocket, CollName, MapData) ->
Path = <<"/_api/document/", CollName/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).
newDocument(PoolNameOrSocket, CollName, MapData, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).
%
% PUT /_api/document/{collection}/{key}
%
%
%
%
% waitForSync
% ignoreRevstrue_rev属性false_rev属性作为前提
% returnOldold属性下
% returnNew new属性下还返回完整的新文档
% true
%
% If-Match使if-match HTTP标头有条件地根据目标修订版ID替换文档
% json
% JSON表示形式
%
% _key属性的值以及用作分片键的属性均不得更改
% If-Match标头
% If-Match且ignoreRevs为false_rev属性
% HTTP 412
% HTTP 201HTTP 202waitForSyncEtag标头字段包含文档的新修订版Location标头包含完整的URLURL下
% ArangoDB可能会回答
% 使waitForSync标志waitForSync仍可用于强制将文档替换操作同步到磁盘waitForSync查询参数可用于强制特定操作的同步使waitForSync参数设置为truewaitForSync参数或将其设置为 falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% silent未设置为trueJSON对象 _id包含更新的文档的已知文档ID_key _rev包含新文档的修订版
% returnOld为trueold属性下返回文档的完整先前修订版
% returnNew为truenew属性下返回完整的新文档
% HTTP 404
%
% 201waitForSync为true
% 202waitForSync为false
% 400JSON表示形式
% 404
% 412_rev _id和_key
replaceDocument(PoolNameOrSocket, CollName, Key, MapData) ->
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], BodyStr).
replaceDocument(PoolNameOrSocket, CollName, Key, MapData, Headers, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, Headers, BodyStr).
%
% PATCH /_api/document/{collection}/{key}
%
%
%
%
% keepNull使patch命令删除现有属性URL查询参数keepNull与false一起使用patch命令的行为null的现有文档
% mergeObjectsfalsetrue true
% waitForSync
% ignoreRevstrue_rev属性false_rev属性作为前提
% returnOldold属性下
% returnNew new属性下还返回完整的新文档
% true
%
% If-Match使if-match HTTP标头有条件地根据目标修订版ID更新文档
% json
% JSON表示形式作为对象
% document-id标识的文档JSON文档
% _key属性的值以及用作分片键的属性均不得更改
% null会导致默认情况下为该属性保存null值
% If-Match标头
% If-Match且ignoreRevs为false_rev属性
% HTTP 412
% HTTP 201HTTP 202waitForSyncEtag标头字段包含文档的新修订版Location标头包含一个可以查询文档的完整URL
% ArangoDB可能会以未发现的错误回答
% 使waitForSync标志waitForSync仍可用于强制将更新的文档操作同步到磁盘waitForSync查询参数可用于强制特定操作的同步使waitForSync参数设置为truewaitForSync参数或将其设置为 falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% silent未设置为trueJSON对象 _id包含更新的文档的已知文档ID_key _rev包含新文档的修订版
% returnOld为trueold属性下返回文档的完整先前修订版
% returnNew为truenew属性下返回完整的新文档
% HTTP 404
%
% 201waitForSync为true
% 202waitForSync为false
% 400JSON表示形式
% 404
% 412_rev _id和_key
updateDocument(PoolNameOrSocket, CollName, Key, MapData) ->
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Patch, Path, [], BodyStr).
updateDocument(PoolNameOrSocket, CollName, Key, MapData, Headers, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Patch, Path, Headers, BodyStr).
%
% DELETE /_api/document/{collection}/{key}
%
%
%
%
% waitForSync
% returnOldold属性下
% true
%
% If-Match使if-match HTTP标头有条件地根据目标修订版ID删除文档
% silent未设置为trueJSON对象 _id包含已删除文档的已知文档ID_key _rev包含文档修订版
% waitForSync参数或将其设置为falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync
% returnOld为trueold属性下返回文档的完整先前修订版
%
% 200waitForSync为true
% 202waitForSync为false
% 404
% 412-match_rev属性中包含找到的文档的当前修订_id和_key
delDocument(PoolNameOrSocket, CollName, Key) ->
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary>>,
agHttpCli:callAgency(PoolNameOrSocket, ?Delete, Path, [], undefined).
delDocument(PoolNameOrSocket, CollName, Key, Headers, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, "/", (agMiscUtils:toBinary(Key))/binary, QueryBinary/binary>>,
agHttpCli:callAgency(PoolNameOrSocket, ?Delete, Path, Headers, undefined).
%
% ArangoDB支持批量处理文档 使API变体可使客户端分摊整批文档中的单个请求的开销ArangoDB
% ArangoDB将继续处理其余操作X-Arango-Error-Codes标头还将包含发生的错误代码及其多重性的映射 1205:10,1210:17101205 171210
% JSON数组
%
% PUT /_api/document/{collection}#get
%
%
%
% onlygettrue
% ignoreRevstrue_rev字段的值
% _key标识的文档_key值JSON数组
% _key字段的值_rev ignoreRevs设置为false
% ArangoDB可能会回答
% _id包含文档标识符_key包含唯一标识给定集合中的文档的键_rev包含修订版
%
% 200
% 400JSON表示形式
% 404
getDocuments(PoolNameOrSocket, CollName, KeyOrMapDataList, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(KeyOrMapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], BodyStr).
%
% POST /_api/document/{collection}#multiple
%
%
%
% ArangoDB版本<3.0URL路径为/ _api / documentURL路径中指定集合
% waitForSync
% returnNew new属性下返回完整的新文档
% returnOld old属性下返回完整的旧文档使
% true
% true_key的文档
% json
%
% _key的文档_key_key
% JSON数组error设置为trueerrorCode设置为发生的错误代码
% _id和_rev属性被忽略URL部分或查询参数集合分别计数
% silent未设置为trueJSON对象数组
% _id包含新创建的文档的文档标识符
% _key包含文档密钥
% _rev包含文档修订版
% collection参数waitForSync为false
% 使waitForSync标志waitForSync也可用于强制将文档创建操作同步到磁盘waitForSync查询参数可用于强制执行此特定操作的同步使waitForSync参数设置为true waitForSync参数或将其设置为falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% returnNew为truenew属性下返回完整的新文档
% HTTP头的文件已经发生了错误的X阿朗戈-120510,121017101205171210
%
% 201waitForSync为true
% 202waitForSync为false并且已处理操作
% 400JSON表示形式
% 404collection指定的collection未知
newDocuments(PoolNameOrSocket, CollName, MapDataList) ->
Path = <<"/_api/document/", CollName/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).
newDocuments(PoolNameOrSocket, CollName, MapDataList, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).
%
% PUT /_api/document/{collection}
%
% URL参数是替换文档的集合的名称
%
% waitForSync
% ignoreRevstrue_rev属性false_rev属性作为前提
% returnOldold属性下还返回更改后的文档的完整先前修订
% returnNew new属性下还返回完整的新文档
% json
% JSON表示形式
% _key属性指定
% _key属性的值以及用作分片键的属性均不得更改
% ignoreRevs为false_rev属性
% ArangoDB可能会回答
% 使waitForSync标志waitForSync仍可用于强制将文档替换操作同步到磁盘waitForSync查询参数可用于强制特定操作的同步使waitForSync参数设置为truewaitForSync参数或将其设置为 falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% JSON数组 _id包含每个更新文档的已知文档ID _key包含用于唯一标识给定集合中的文档的键_rev包含新文档修订版error设置为true errorCode设置为错误代码
% returnOld为trueold属性下返回文档的完整先前修订版
% returnNew为truenew属性下返回完整的新文档
% 201202HTTP标头X-Arango-Error-Codes120017,120510171200101205
%
% 201waitForSync为true
% 202waitForSync为false并且已处理操作
% 400JSON表示形式
% 404
replaceDocuments(PoolNameOrSocket, CollName, MapDataList) ->
Path = <<"/_api/document/", CollName/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], BodyStr).
replaceDocuments(PoolNameOrSocket, CollName, MapDataList, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Put, Path, [], BodyStr).
%
% PATCH /_api/document/{collection}
%
%
%
% keepNull使patch命令删除现有属性URL查询参数keepNull与false一起使用patch命令的行为null的现有文档
% mergeObjectsfalsetrue true
% waitForSync
% ignoreRevstrue_rev属性false_rev属性作为前提
% returnOldold属性下还返回更改后的文档的完整先前修订
% returnNew new属性下还返回完整的新文档
% json
% JSON表示形式是对象
% _key属性指定JSON数组
% _key属性的值以及用作分片键的属性均不得更改
% null会导致默认情况下为该属性保存null值
% ignoreRevs为false_rev属性
% ArangoDB可能会以未发现的错误回答
% 使waitForSync标志waitForSync仍可用于强制将文档替换操作同步到磁盘waitForSync查询参数可用于强制特定操作的同步使waitForSync参数设置为truewaitForSync参数或将其设置为 falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync值为true
% JSON数组 _id包含每个更新文档的已知文档ID _key包含用于唯一标识给定集合中的文档的键_rev包含新文档修订版error设置为true errorCode设置为错误代码
% returnOld为trueold属性下返回文档的完整先前修订版
% returnNew为truenew属性下返回完整的新文档
% 201202HTTP标头X-Arango-Error-Codes120017,120510171200101205
%
% 201waitForSync为true
% 202waitForSync为false并且已处理操作
% 400JSON表示形式
% 404
updateDocuments(PoolNameOrSocket, CollName, MapDataList) ->
Path = <<"/_api/document/", CollName/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Patch, Path, [], BodyStr).
updateDocuments(PoolNameOrSocket, CollName, MapDataList, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(MapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Patch, Path, [], BodyStr).
%
% DELETE /_api/document/{collection}
%
%
%
% waitForSync
% returnOldold属性下
% ignoreRevstrue_rev属性
% json
% JSON数组
% _key属性的对象API调用从collection中删除所有指定的文档_rev属性
% JSON对象_id包含已删除文档的已知文档ID_key包含用于唯一标识给定集合中的文档的键_rev包含文档修订版 errorCode集到的错误代码被构建的
% waitForSync参数或将其设置为falsewaitForSync行为waitForSync查询参数不能用于禁用同步用于具有默认集合waitForSync
% returnOld为trueold属性下返回文档的完整先前修订版
% 200202HTTP标头X-Arango-Error-Codes120017,120510171200101205
%
% 200waitForSync为true
% 202waitForSync为false
% 404
delDocuments(PoolNameOrSocket, CollName, KeyOrMapDataList) ->
Path = <<"/_api/document/", CollName/binary, "/">>,
BodyStr = jiffy:encode(KeyOrMapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Delete, Path, [], BodyStr).
delDocuments(PoolNameOrSocket, CollName, KeyOrMapDataList, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/document/", CollName/binary, QueryBinary/binary>>,
BodyStr = jiffy:encode(KeyOrMapDataList),
agHttpCli:callAgency(PoolNameOrSocket, ?Delete, Path, [], BodyStr).

+ 26
- 0
src/arangoApi/agEdges.erl Переглянути файл

@ -0,0 +1,26 @@
-module(agEdges).
-include("erlArango.hrl").
-compile([export_all, nowarn_export_all]).
%% doc_address:https://www.arangodb.com/docs/stable/http/edge.html
% _from和_tofrom和to顶点的文档句柄
% 使 REST api ///
%
%
% GET /_api/edges/{collection-id}
%
% collection-idID
%
% ID
%
% vertex标识的顶点开始或结束的边数组
%
% 200
% 400
% 404
getEdges(PoolNameOrSocket, CollName, QueryPars) ->
QueryBinary = agMiscUtils:spellQueryPars(QueryPars),
Path = <<"/_api/edges/", CollName/binary, QueryBinary/binary>>,
agHttpCli:callAgency(PoolNameOrSocket, ?Get, Path, [], undefined).

+ 82
- 0
src/arangoApi/agGeneralGraphs.erl Переглянути файл

@ -0,0 +1,82 @@
-module(agGeneralGraphs).
-include("erlArango.hrl").
-compile([export_all, nowarn_export_all]).
%% doc_address:https://www.arangodb.com/docs/stable/http/gharial.html
%
% GET /_api/gharial
%
% HTTP 200
% errortruefalse
% code
%
% graph
% name
% edgeDefinitions
% orphanCollections
% numberOfShards
% _idID值
% _rev
% ReplicationFactor使
% isSmartSmartGraph
% smartGraphAttribute
getGharial(PoolNameOrSocket) ->
agHttpCli:callAgency(PoolNameOrSocket, ?Get, <<"/_api/gharial">>, [], undefined).
%
% POST /_api/gharial
%
% waitForSync
% JSON对象是必需的
% name
% edgeDefinitions
% orphanCollections
% isSmart
% optionsJSON对象
% smartGraphAttributeisSmart为trueSmartGraph中的每个顶点都必须具有此属性
% numberOfShards使
% 使
% writeConcernDBServer上同步每个分片需要多少个副本writeConcern的值 ReplicationFactor
%
% _graphs集合启用了waitForSync HTTP 201
% errortruefalse
% code
% graph
% _graphs集合禁用了waitForSyncHTTP 202
% errortruefalse
% code
% graph
% HTTP 400
% errortruefalse
% code
% errorNumArangoDB错误号
% errorMessage
% HTTP 403
% Administrate 访
% Read Only 访使
% errortruefalse
% code
% errorNumArangoDB错误号
% errorMessage
% HTTP 409使
% errortruefalse
% code
% errorNumArangoDB错误号
% errorMessage
newGharial(PoolNameOrSocket, MapData) ->
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, <<"/_api/gharial">>, [], BodyStr).
newGharial(PoolNameOrSocket, MapData, WaitForSync) ->
Path =
case WaitForSync of
true ->
<<"/_api/gharial?waitForSync=true">>;
_ ->
<<"/_api/gharial?waitForSync=false">>
end,
BodyStr = jiffy:encode(MapData),
agHttpCli:callAgency(PoolNameOrSocket, ?Post, Path, [], BodyStr).

+ 11
- 0
src/httpCli/agMiscUtils.erl Переглянути файл

@ -12,6 +12,7 @@
, getListValue/3
, randomElement/1
, toBinary/1
, spellQueryPars/1
]).
-spec parseUrl(binary()) -> dbOpts() | {error, invalid_url}.
@ -94,3 +95,13 @@ toBinary(Value) when is_binary(Value) -> Value;
toBinary([Tuple | PropList] = Value) when is_list(PropList) and is_tuple(Tuple) ->
lists:map(fun({K, V}) -> {toBinary(K), toBinary(V)} end, Value);
toBinary(Value) -> term_to_binary(Value).
-spec spellQueryPars(list()) -> binary().
spellQueryPars([]) ->
<<>>;
spellQueryPars([{Key, Value}]) ->
<<"?", (toBinary(Key))/binary, "=", (toBinary(Value))/binary>>;
spellQueryPars([{Key, Value} | Tail]) ->
First = <<"?", (toBinary(Key))/binary, "=", (toBinary(Value))/binary>>,
Tail = [<<"&", (toBinary(OtherKey))/binary, "=", (toBinary(OtherValue))/binary>> || {OtherKey, OtherValue} <- Tail],
<<First/binary, Tail/binary>>.

Завантаження…
Відмінити
Зберегти