| <!DOCTYPE html> |
| <html> |
| <head> |
| <meta http-equiv="content-type" content="text/html;charset=utf-8"> |
| <title>multi_put</title> |
| <link rel="stylesheet" href="/css/pycco.css"> |
| </head> |
| <body> |
| <div id="background"></div> |
| <div id='container'> |
| <div class='section'> |
| <div class='docs'><h1>multi_put</h1></div> |
| </div> |
| <div class='clearall'> |
| <div class='section' id='section-0'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-0'>#</a> |
| </div> |
| <p>If you have not yet seen the source in <a href="/examples/basic_with_auth.html">basic_with_auth</a>, please take a look.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-1'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-1'>#</a> |
| </div> |
| <p>In this sample we expand on authenticated insertion of a single entity |
| by showing how to insert a collection of entities at once while |
| requiring that the user is authenticated.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-1'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-2'>#</a> |
| </div> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre><span class="kn">import</span> <span class="nn">endpoints</span> |
| |
| <span class="kn">from</span> <span class="nn">google.appengine.ext</span> <span class="kn">import</span> <span class="n">ndb</span> |
| <span class="kn">from</span> <span class="nn">protorpc</span> <span class="kn">import</span> <span class="n">remote</span> |
| |
| <span class="kn">from</span> <span class="nn">endpoints_proto_datastore.ndb</span> <span class="kn">import</span> <span class="n">EndpointsModel</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-3'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-3'>#</a> |
| </div> |
| |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre><span class="k">class</span> <span class="nc">MyModel</span><span class="p">(</span><span class="n">EndpointsModel</span><span class="p">):</span> |
| <span class="n">attr1</span> <span class="o">=</span> <span class="n">ndb</span><span class="o">.</span><span class="n">StringProperty</span><span class="p">()</span> |
| <span class="n">attr2</span> <span class="o">=</span> <span class="n">ndb</span><span class="o">.</span><span class="n">StringProperty</span><span class="p">()</span> |
| <span class="n">created</span> <span class="o">=</span> <span class="n">ndb</span><span class="o">.</span><span class="n">DateTimeProperty</span><span class="p">(</span><span class="n">auto_now_add</span><span class="o">=</span><span class="bp">True</span><span class="p">)</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-4'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-4'>#</a> |
| </div> |
| |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre><span class="nd">@endpoints.api</span><span class="p">(</span><span class="n">name</span><span class="o">=</span><span class="s">'myapi'</span><span class="p">,</span> <span class="n">version</span><span class="o">=</span><span class="s">'v1'</span><span class="p">,</span> <span class="n">description</span><span class="o">=</span><span class="s">'My Little API'</span><span class="p">)</span> |
| <span class="k">class</span> <span class="nc">MyApi</span><span class="p">(</span><span class="n">remote</span><span class="o">.</span><span class="n">Service</span><span class="p">):</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-5'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-5'>#</a> |
| </div> |
| <p>In standard usage, there is no default way to use <code>request_fields</code> |
| to turn a method that accepts an <code>EndpointsModel</code> subtype into one |
| that accepts a collection of items of the same subtype.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-6'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-6'>#</a> |
| </div> |
| <p>However, <code>EndpointsModel.method</code> accepts an alternate keyword argument |
| which allows this: <code>request_message</code>.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-7'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-7'>#</a> |
| </div> |
| <p>By specifying <code>request_message</code> (and/or |
| <code>response_message</code>), the ProtoRPC definition |
| of the request can be directly provided to the method.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-8'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-8'>#</a> |
| </div> |
| <p>In order to get the ProtoRPC definition for a collection, we use the |
| <code>EndpointsModel.ProtoCollection</code> utility which is used to form the |
| responses in <code>EndpointsModel.query_method</code>.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre> <span class="nd">@MyModel.method</span><span class="p">(</span><span class="n">request_message</span><span class="o">=</span><span class="n">MyModel</span><span class="o">.</span><span class="n">ProtoCollection</span><span class="p">(),</span> |
| <span class="n">response_message</span><span class="o">=</span><span class="n">MyModel</span><span class="o">.</span><span class="n">ProtoCollection</span><span class="p">(),</span> |
| <span class="n">user_required</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> |
| <span class="n">path</span><span class="o">=</span><span class="s">'mymodel_multi'</span><span class="p">,</span> |
| <span class="n">name</span><span class="o">=</span><span class="s">'mymodel.insert_multi'</span><span class="p">)</span> |
| <span class="k">def</span> <span class="nf">MyModelMultiInsert</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">my_model_collection</span><span class="p">):</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-9'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-9'>#</a> |
| </div> |
| <p>Convert the RPC messages into the corresponding |
| <code>ndb</code> entities. This is necessary because using |
| <code>request_fields</code> makes the request |
| object a raw ProtoRPC message of the given type. |
| </p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre> <span class="n">entities</span> <span class="o">=</span> <span class="p">[</span><span class="n">MyModel</span><span class="o">.</span><span class="n">FromMessage</span><span class="p">(</span><span class="n">item_msg</span><span class="p">)</span> |
| <span class="k">for</span> <span class="n">item_msg</span> <span class="ow">in</span> <span class="n">my_model_collection</span><span class="o">.</span><span class="n">items</span><span class="p">]</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-10'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-10'>#</a> |
| </div> |
| <p>Efficiently write the entities to datastore.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre> <span class="n">ndb</span><span class="o">.</span><span class="n">put_multi</span><span class="p">(</span><span class="n">entities</span><span class="p">)</span></pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-11'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-11'>#</a> |
| </div> |
| <p>Since the response type is hardcoded as a ProtoRPC message type, the |
| ProtoRPC message must be directly returned. This is different than |
| the typical flow using <code>response_fields</code> since the current method |
| doesn't know how to convert the response from a native <code>ndb.Model</code> |
| into a ProtoRPC message.</p> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre> <span class="n">response_items</span> <span class="o">=</span> <span class="p">[</span><span class="n">entity</span><span class="o">.</span><span class="n">ToMessage</span><span class="p">()</span> <span class="k">for</span> <span class="n">entity</span> <span class="ow">in</span> <span class="n">entities</span><span class="p">]</span> |
| <span class="n">response_collection</span> <span class="o">=</span> <span class="n">MyModel</span><span class="o">.</span><span class="n">ProtoCollection</span><span class="p">()(</span><span class="n">items</span><span class="o">=</span><span class="n">response_items</span><span class="p">)</span> |
| </pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| <div class='section' id='section-12'> |
| <div class='docs'> |
| <div class='octowrap'> |
| <a class='octothorpe' href='#section-12'>#</a> |
| </div> |
| </div> |
| <div class='code'> |
| <div class="highlight"><pre> <span class="k">return</span> <span class="n">response_collection</span> |
| |
| |
| <span class="n">application</span> <span class="o">=</span> <span class="n">endpoints</span><span class="o">.</span><span class="n">api_server</span><span class="p">([</span><span class="n">MyApi</span><span class="p">],</span> <span class="n">restricted</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span> |
| |
| </pre></div> |
| </div> |
| </div> |
| <div class='clearall'></div> |
| </div> |
| </body> |