You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@couchdb.apache.org by da...@apache.org on 2019/11/19 18:21:16 UTC

[couchdb-local] 07/16: Add local:otp_name/1 and local:which_processes/{1, 2}

This is an automated email from the ASF dual-hosted git repository.

davisp pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/couchdb-local.git

commit d8d21b3b66f0999af985f7f06d634e74860218e0
Author: Takeru Ohta <ph...@gmail.com>
AuthorDate: Tue Oct 7 02:18:39 2014 +0900

    Add local:otp_name/1 and local:which_processes/{1,2}
---
 doc/local.md              | 67 +++++++++++++++++++++++++++++++++++++++++++++--
 rebar.config.script       |  8 ++++++
 src/local.erl             | 35 +++++++++++++++++++++++++
 src/local_name_server.erl | 19 ++++++++++++++
 test/local_tests.erl      | 25 ++++++++++++++++++
 5 files changed, 152 insertions(+), 2 deletions(-)

diff --git a/doc/local.md b/doc/local.md
index ba8f4fa..7d3eaf8 100644
--- a/doc/local.md
+++ b/doc/local.md
@@ -42,6 +42,30 @@ name_server_name() = atom()
 
 
 
+### <a name="type-otp_name">otp_name()</a> ###
+
+
+
+<pre><code>
+otp_name() = {local, Name::atom()} | {global, Name::term()} | {via, module(), Name::term()}
+</code></pre>
+
+
+
+
+
+### <a name="type-otp_ref">otp_ref()</a> ###
+
+
+
+<pre><code>
+otp_ref() = (Name::atom()) | {Name::atom(), node()} | {global, Name::term()} | {via, module(), Name::term()} | pid()
+</code></pre>
+
+
+
+
+
 ### <a name="type-process_name">process_name()</a> ###
 
 
@@ -56,7 +80,7 @@ process_name() = term()
 ## Function Index ##
 
 
-<table width="100%" border="1" cellspacing="0" cellpadding="2" summary="function index"><tr><td valign="top"><a href="#name_server_child_spec-1">name_server_child_spec/1</a></td><td>Equivalent to <a href="#name_server_child_spec-3"><tt>name_server_child_spec(Name, Name, 5000)</tt></a>.</td></tr><tr><td valign="top"><a href="#name_server_child_spec-3">name_server_child_spec/3</a></td><td>Returns the child spec for a local name server that is used in embedded mode.</td></tr><tr><td valign= [...]
+<table width="100%" border="1" cellspacing="0" cellpadding="2" summary="function index"><tr><td valign="top"><a href="#name_server_child_spec-1">name_server_child_spec/1</a></td><td>Equivalent to <a href="#name_server_child_spec-3"><tt>name_server_child_spec(Name, Name, 5000)</tt></a>.</td></tr><tr><td valign="top"><a href="#name_server_child_spec-3">name_server_child_spec/3</a></td><td>Returns the child spec for a local name server that is used in embedded mode.</td></tr><tr><td valign= [...]
 
 
 <a name="functions"></a>
@@ -91,7 +115,20 @@ name_server_child_spec(ChildId, ServerName, Shutdown) -&gt; ChildSpec
 Returns the child spec for a local name server that is used in embedded mode.
 
 
-To embed a local name server in your application, you can add the child spec `ChildSpec` to your supervision tree.
+To embed a local name server in your application, you can simply add `ChildSpec` to your supervision tree.
+<a name="otp_name-1"></a>
+
+### otp_name/1 ###
+
+
+<pre><code>
+otp_name(Name::<a href="#type-name">name()</a>) -&gt; <a href="#type-otp_name">otp_name()</a>
+</code></pre>
+
+<br></br>
+
+
+Returns OTP compatible name
 <a name="register_name-2"></a>
 
 ### register_name/2 ###
@@ -220,3 +257,29 @@ which_name_servers() -&gt; [<a href="#type-name_server_name">name_server_name()<
 
 
 Returns a list of running name server
+<a name="which_processes-1"></a>
+
+### which_processes/1 ###
+
+
+<pre><code>
+which_processes(NameServer::<a href="#type-name_server_name">name_server_name()</a>) -&gt; [{<a href="#type-process_name">process_name()</a>, pid()}]
+</code></pre>
+
+<br></br>
+
+
+Returns a list of registered process
+<a name="which_processes-2"></a>
+
+### which_processes/2 ###
+
+
+<pre><code>
+which_processes(NameServer::<a href="#type-name_server_name">name_server_name()</a>, Pattern::<a href="ets.md#type-match_pattern">ets:match_pattern()</a>) -&gt; [{<a href="#type-process_name">process_name()</a>, pid()}]
+</code></pre>
+
+<br></br>
+
+
+Returns a list of registered process that has a name which matches the pattern `Pattern`
diff --git a/rebar.config.script b/rebar.config.script
new file mode 100644
index 0000000..fa7d969
--- /dev/null
+++ b/rebar.config.script
@@ -0,0 +1,8 @@
+%% vim: set ft=erlang : -*- erlang -*-
+
+case erlang:system_info(version) < "6" of
+    false -> CONFIG;
+    true  ->
+        ErlOpts = proplists:get_value(erl_opts, CONFIG, []) ++ [{d, 'LOCAL_BEFORE_OTP17'}],
+        proplists:delete(erl_opts, CONFIG) ++ [{erl_opts, ErlOpts}]
+end.
diff --git a/src/local.erl b/src/local.erl
index 5eb128e..9ec5975 100644
--- a/src/local.erl
+++ b/src/local.erl
@@ -14,12 +14,17 @@
 -export([unregister_name/1]).
 -export([whereis_name/1]).
 -export([send/2]).
+-export([which_processes/1, which_processes/2]).
 
 -export([name_server_child_spec/1, name_server_child_spec/3]).
 
+-export([otp_name/1]).
+
 -export_type([name/0]).
 -export_type([name_server_name/0]).
 -export_type([process_name/0]).
+-export_type([otp_name/0]).
+-export_type([otp_ref/0]).
 
 %%----------------------------------------------------------------------------------------------------------------------
 %% Macros & Types
@@ -28,6 +33,16 @@
 -type name_server_name() :: atom().
 -type process_name() :: term().
 
+-type otp_name() :: {local, Name :: atom()}
+                  | {global, Name :: term()}
+                  | {via, module(), Name :: term()}.
+
+-type otp_ref() :: (Name :: atom())
+                 | {Name :: atom(), node()}
+                 | {global, Name :: term()}
+                 | {via, module(), Name :: term()}
+                 | pid().
+
 %%----------------------------------------------------------------------------------------------------------------------
 %% Exported Functions
 %%----------------------------------------------------------------------------------------------------------------------
@@ -97,6 +112,16 @@ send(Name, Msg) ->
         Pid       -> _ = Pid ! Msg, Pid
     end.
 
+%% @doc Returns a list of registered process
+-spec which_processes(name_server_name()) -> [{process_name(), pid()}].
+which_processes(NameServer) ->
+    local_name_server:which_processes(NameServer).
+
+%% @doc Returns a list of registered process that has a name which matches the pattern `Pattern'
+-spec which_processes(name_server_name(), ets:match_pattern()) -> [{process_name(), pid()}].
+which_processes(NameServer, ProcNamePattern) ->
+    local_name_server:which_processes(NameServer, ProcNamePattern).
+
 %% @equiv name_server_child_spec(Name, Name, 5000)
 -spec name_server_child_spec(name_server_name()) -> supervisor:child_spec().
 name_server_child_spec(Name) ->
@@ -114,3 +139,13 @@ name_server_child_spec(ChildId, ServerName, Shutdown) when is_atom(ServerName) -
     {ChildId, {local_name_server, start_link, [ServerName]}, permanent, Shutdown, worker, [local_name_server]};
 name_server_child_spec(ChildId, ServerName, Shutdown) ->
     error(badarg, [ChildId, ServerName, Shutdown]).
+
+%% @doc Returns OTP compatible name
+-spec otp_name(name()) -> otp_name().
+-ifdef('LOCAL_BEFORE_OTP17').
+otp_name(Name) ->
+    list_to_tuple([via, local, Name]).
+-else.
+otp_name(Name) ->
+    {via, local, Name}.
+-endif.
diff --git a/src/local_name_server.erl b/src/local_name_server.erl
index a9b5391..da0ac6b 100644
--- a/src/local_name_server.erl
+++ b/src/local_name_server.erl
@@ -13,6 +13,7 @@
 -export([register_name/3]).
 -export([unregister_name/2]).
 -export([whereis_name/2]).
+-export([which_processes/1, which_processes/2]).
 
 %%----------------------------------------------------------------------------------------------------------------------
 %% 'gen_server' Callback API
@@ -57,6 +58,24 @@ whereis_name(Server, Name) ->
         _:_ -> undefined
     end.
 
+%% @see local:which_processes/1
+-spec which_processes(local:name_server_name()) -> [{local:process_name(), pid()}].
+which_processes(Server) ->
+    try
+        ets:tab2list(Server)
+    catch
+        _:_ -> []
+    end.
+
+%% @see local:which_processes/2
+-spec which_processes(local:name_server_name(), ets:match_pattern()) -> [{local:process_name(), pid()}].
+which_processes(Server, ProcNamePattern) ->
+    try
+        ets:match_object(Server, {ProcNamePattern, '_'})
+    catch
+        _:_ -> []
+    end.
+
 %%----------------------------------------------------------------------------------------------------------------------
 %% 'gen_server' Callback Functions
 %%----------------------------------------------------------------------------------------------------------------------
diff --git a/test/local_tests.erl b/test/local_tests.erl
index 042890b..dad6fdf 100644
--- a/test/local_tests.erl
+++ b/test/local_tests.erl
@@ -195,6 +195,31 @@ gen_server_test_() ->
        end}
      ]}.
 
+which_processes_test_() ->
+    {foreach,
+     fun ()  -> ok = local:start_name_server(?NS) end,
+     fun (_) -> ok = local:stop_name_server(?NS) end,
+     [
+      {"get a list of registered process",
+       fun () ->
+               ?assertEqual([], local:which_processes(?NS)),
+
+               yes = local:register_name(?NAME(hoge), self()),
+               ?assertEqual([{hoge, self()}], local:which_processes(?NS)),
+
+               ok = local:unregister_name(?NAME(hoge)),
+               ?assertEqual([], local:which_processes(?NS))
+       end},
+      {"get a filtered list of registered process",
+       fun () ->
+               yes = local:register_name(?NAME(hoge), self()),
+
+               ?assertEqual([],               local:which_processes(?NS, fuga)),
+               ?assertEqual([{hoge, self()}], local:which_processes(?NS, hoge)),
+               ?assertEqual([{hoge, self()}], local:which_processes(?NS, '_'))
+       end}
+     ]}.
+
 %%----------------------------------------------------------------------------------------------------------------------
 %% Internal Functions
 %%----------------------------------------------------------------------------------------------------------------------