<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
	<channel>
		<description>Posts by Kanat</description>
		<url>https://bekt.net</url>
		<atom:link href="https://bekt.net/feed.xml" rel="self" type="application/rss+xml" />
		
			<item>
				<title>AngularJS: Reducing Initial Load Time by Preloading Data</title>
				<excerpt>&lt;h2 id=&quot;background&quot;&gt;Background&lt;/h2&gt;
</excerpt>
				<content>&lt;h2 id=&quot;background&quot;&gt;Background&lt;/h2&gt;

&lt;p&gt;Most of the web has transitioned into client-side heavy development using
various JavaScript frameworks. More and more sites are being built in
the “Single Page Application” (SPA) fashion. This puts more work on the user’s browser
and less work on the servers. The shift keeps front-end and back-end development
separate and isolated, allowing clients to present information in different ways without
relying on server-side rendering. Additionally, most of smartphones these days
are more powerful than servers that serve thousands of users.&lt;/p&gt;

&lt;p&gt;[ &lt;a href=&quot;https://plnkr.co/edit/og8aqTSLU6IrpaHqX56O&quot;&gt;Source Code&lt;/a&gt;
| &lt;a href=&quot;https://run.plnkr.co/plunks/og8aqTSLU6IrpaHqX56O&quot;&gt;Demo&lt;/a&gt; ]&lt;/p&gt;

&lt;p&gt;One of the most common issues with this paradigm is the slow initial load time
of the page. Typically, the page is loaded very quickly only to show a spinning
icon for some time until the actual content is loaded. Here’s the diagram
that explains the request cycle:&lt;/p&gt;

&lt;p&gt;&lt;a href=&quot;//i.imgur.com/nQjRqXe.png&quot;&gt;&lt;img src=&quot;//i.imgur.com/nQjRqXel.png&quot; alt=&quot;&quot; /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;Client requests the page. Server responds with some bootstrapped and
non-rendered HTML. (green)&lt;/li&gt;
  &lt;li&gt;Client requests for static assets, including the JavaScript files and HTML templates. (blue)&lt;/li&gt;
  &lt;li&gt;Application makes one or more HTTP calls to fetch various resources. (yellow)&lt;/li&gt;
  &lt;li&gt;The loaded resources are displayed to the user.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;These steps are sequential. As one can imagine, the initial load time
can be very slow if the user has a slow internet connection and/or the user
is far away from the website data centers.&lt;/p&gt;

&lt;p&gt;By looking at the diagram, let’s assume the &lt;code&gt;api/products/123&lt;/code&gt; is the highest
priority HTTP call. We want to show the result of it as soon as it is ready
while other HTTP calls may still be pending. If we somehow include the response of
this endpoint with the initial HTML page or &lt;code&gt;app.js&lt;/code&gt;, the extra HTTP call
would not be necessary.&lt;/p&gt;

&lt;h2 id=&quot;angularjs-and-angular-ui-router&quot;&gt;AngularJS and Angular UI Router&lt;/h2&gt;

&lt;p&gt;&lt;a href=&quot;https://angularjs.org/&quot;&gt;AngularJS&lt;/a&gt; is a popular and somewhat opinionated
JavaScript framework that is backed by Google.
(Fun fact: the Angular team sat one floor below my team at Google!)&lt;/p&gt;

&lt;blockquote&gt;
  &lt;p&gt;AngularJS lets you write client-side web applications as if you had a smarter browser.
It lets you use good old HTML (or HAML, Jade and friends!) as your template language and
lets you extend HTML’s syntax to express your application’s components clearly and succinctly.
It automatically synchronizes data from your UI (view) with your JavaScript objects (model)
through 2-way data binding.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;If you are building an &lt;em&gt;AngularJS 1.x&lt;/em&gt; app, you probably are already familiar with
&lt;a href=&quot;https://github.com/angular-ui/ui-router&quot;&gt;AngularUI Router&lt;/a&gt;. It is generally
more flexible than the standard &lt;a href=&quot;https://docs.angularjs.org/api/ngRoute/service/$route&quot;&gt;&lt;code&gt;$route&lt;/code&gt;&lt;/a&gt;
service. I suggest looking into it if you have not done so.
The example in this post uses AngularUI Router.&lt;/p&gt;

&lt;p&gt;A typical application route setup might look something like this:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;js&quot;&gt;$stateProvider
    .state(&amp;#39;main&amp;#39;, {
        abstract: true,
        resolve: {
            user: function (UserService) {
                return UserService.me();
            }
        }
    .state(&amp;#39;main.product&amp;#39;, {
        url: &amp;#39;/products/{id}&amp;#39;
        resolve: {
            product: function ($stateParams, ItemService) {
                return ItemService.get($stateParams.id);
            }
        }
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The &lt;code&gt;user&lt;/code&gt; and &lt;code&gt;product&lt;/code&gt; properties are “resolved” (by making HTTP calls for example)
before the state transition happens.&lt;/p&gt;

&lt;h2 id=&quot;preload-prefetch-data&quot;&gt;Preload (Prefetch) Data&lt;/h2&gt;

&lt;p&gt;The solution I propose is simple but somewhat ugly to implement.
It minimizes the initial load time, which is the best user experience.&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;When the server receives a request to &lt;code&gt;website.com/products/123&lt;/code&gt;, it makes
an API call to &lt;code&gt;api/products/123&lt;/code&gt; on behalf of the client.
This will be significantly faster than the client calling the API endpoint because
the data centers are typically close to each other with much faster network speeds.&lt;/li&gt;
  &lt;li&gt;The result from &lt;code&gt;api/products/123&lt;/code&gt; is appended to the original as URL parameter
(let’s call it &lt;code&gt;_data&lt;/code&gt;). The URL change to: &lt;code&gt;website.com/products/123?_data={...}&lt;/code&gt;&lt;/li&gt;
  &lt;li&gt;The client handles the case when this URL parameter is present.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Important&lt;/strong&gt;: In order for the proposed solution to work, the application
needs to have
&lt;a href=&quot;https://code.angularjs.org/1.4.7/docs/api/ng/provider/$locationProvider#html5Mode&quot;&gt;html5Mode&lt;/a&gt;
enabled. This is because anything after the &lt;code&gt;#&lt;/code&gt; portion of the URL is not sent
to the server (read more: &lt;a href=&quot;https://en.wikipedia.org/wiki/Fragment_identifier&quot;&gt;fragment identifier&lt;/a&gt;).
The default hashbang method uses the &lt;code&gt;#&lt;/code&gt;. You should have strong reasons if
you do not already have html5Mode enabled.&lt;/p&gt;

&lt;p&gt;In this scenario, we are only working with &lt;code&gt;api/products/123&lt;/code&gt;. The solution
can be used in 100 different ways, including but not limited to calling multiple APIs or
including some placeholder data.&lt;/p&gt;

&lt;p&gt;First, let’s make that URL parameter an optional parameter (&lt;code&gt;_data&lt;/code&gt;).&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;js&quot;&gt;class Config {
    constructor($locationProvider, $stateProvider, $urlRouterProvider) {
        $locationProvider.html5Mode(true);

        $urlRouterProvider.otherwise(&amp;#39;/&amp;#39;);

        $stateProvider
            .state(&amp;#39;default&amp;#39;, {
                url: &amp;#39;/&amp;#39;,
                templateUrl: &amp;#39;main.html&amp;#39;
            })
            .state(&amp;#39;item&amp;#39;, {
                url: &amp;#39;/items/{id}?_data&amp;#39;,
                controller: &amp;#39;Item as item&amp;#39;,
                templateUrl: &amp;#39;item.html&amp;#39;,
                reloadOnSearch: false
        });
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;It makes sense to remove the &lt;code&gt;_data&lt;/code&gt; parameter from the URL as soon as the
application reads so the user does not share or bookmark the full URL
(and to make the URL look pretty). The &lt;code&gt;reloadOnSearch: false&lt;/code&gt; option prevents
the state from being reloaded when this happens.&lt;/p&gt;

&lt;p&gt;Now, the client logic skips the API call to get product information
when the &lt;code&gt;_data&lt;/code&gt; parameter is present.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;js&quot;&gt;class Item {
    constructor($log, $state, $stateParams, ItemService) {
        this.title = &amp;#39;Loading..&amp;#39;;
        this._log = $log;
        this._state = $state;
        this._stateParams = $stateParams;
        this._ItemService = ItemService;

        this.init();
    }

    init() {
        let context = this;

        this._log.debug(this._stateParams);

        // Pre-fetched data can come as a URL parameter (`_data`).
        var data = angular.fromJson(this._stateParams._data);

        if (data) {
            // Remove `_data` parameter from URL.
            this._state.go(&amp;#39;.&amp;#39;, {_data: null}, {location: &amp;#39;replace&amp;#39;});

            return ready(data);
        }

        this._ItemService.fetchItem(this._stateParams.id).then(ready, ready);

        function ready(data) {
            context.title = data.name;
            context.item = data;
        }  
    }
}

class ItemService {
    constructor($timeout) {
        this._timeout = $timeout;
    }

    fetchItem(id) {
      return this._timeout(() =&amp;gt; {
          return {id: id, name: &amp;#39;TV&amp;#39;, description: &amp;#39;Fetched from the backend&amp;#39;};
      }, 1500);
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This method reduces the number of HTTP requests made by the application.
However, I do not recommend doing this everywhere in the application as it
introduces logic code both in the back-end endpoint and in the Angular
application.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Full source and demo can be found &lt;a href=&quot;https://run.plnkr.co/plunks/og8aqTSLU6IrpaHqX56O&quot;&gt;here&lt;/a&gt;.&lt;/strong&gt;&lt;/p&gt;

&lt;h2 id=&quot;conclusion&quot;&gt;Conclusion&lt;/h2&gt;

&lt;p&gt;We have looked at one of the biggest concerns against modern client-side heavy
development – slower initial load times. We proposed a back-end agnostic solution
for the problem in AngularJS that makes use of URL parameters. Code samples for
both front-end and back-end have been provided.&lt;/p&gt;

&lt;h2 id=&quot;bonus-flask-back-end-endpoint-handler&quot;&gt;Bonus: Flask Back-end Endpoint Handler&lt;/h2&gt;

&lt;p&gt;Below is the quick implementation of step-1 and step-2 of the proposed solution above,
in &lt;a href=&quot;http://flask.pocoo.org/&quot;&gt;Flask&lt;/a&gt;.
I’m sure a similar approach can be implemented in other frameworks.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;py&quot;&gt;try:
    from urllib.parse import urlencode
except:
    from urllib import urlencode

import re
import flask as f

app = f.Flask(__name__)
ITEMS_RE = re.compile(r&amp;#39;^items/(\d+)&amp;#39;)

@app.route(&amp;#39;/app/&amp;#39;, defaults={&amp;#39;path&amp;#39;: &amp;#39;&amp;#39;})
@app.route(&amp;#39;/app/&amp;lt;path:path&amp;gt;&amp;#39;)
def index(path):
    &amp;quot;&amp;quot;&amp;quot;Main application entry. Let&amp;#39;s assume our app is served at `/app`.&amp;quot;&amp;quot;&amp;quot;
    m = ITEMS_RE.match(path)
    if m and not f.request.args.get(&amp;#39;_data&amp;#39;):
        data = get_item(int(m.groups()[0]))
        args = dict(f.request.args)
        args[&amp;#39;_data&amp;#39;] = f.json.dumps(data)
        url = &amp;#39;{}?{}&amp;#39;.format(f.request.base_url, urlencode(args, doseq=True))
        return f.redirect(url)
    return &amp;#39;return index.html&amp;#39;


def get_item(ident):
    return {&amp;#39;id&amp;#39;: ident, &amp;#39;name&amp;#39;: &amp;#39;fake&amp;#39;, &amp;#39;description&amp;#39;: &amp;#39;fake api return&amp;#39;}


if __name__ == &amp;#39;__main__&amp;#39;:
    app.run(debug=True)
&lt;/code&gt;&lt;/pre&gt;
</content>
				<published>2015-12-28 00:00:00 +0000</published>
				<url>https://bekt.net/p/angular-prefetch/</url>
				<guid isPermaLink="true">https://bekt.net/p/angular-prefetch/</guid>
			</item>
		
			<item>
				<title>Handling Unexpected WTForms Default Values</title>
				<excerpt>&lt;p&gt;The &lt;a href=&quot;https://github.com/wtforms/wtforms&quot;&gt;WTForms&lt;/a&gt; library is great for
working with forms and validations. However, it does not work well with
JSON form data. Specifically, fields that were not provided in the request
are assigned default values. This causes problems when you expect &lt;code&gt;PATCH&lt;/code&gt;-like
requests. Example:&lt;/p&gt;
</excerpt>
				<content>&lt;p&gt;The &lt;a href=&quot;https://github.com/wtforms/wtforms&quot;&gt;WTForms&lt;/a&gt; library is great for
working with forms and validations. However, it does not work well with
JSON form data. Specifically, fields that were not provided in the request
are assigned default values. This causes problems when you expect &lt;code&gt;PATCH&lt;/code&gt;-like
requests. Example:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;py&quot;&gt;import wtforms

class MyBaseForm(wtforms.Form):
    pass

class FooForm(MyBaseForm):
    foo = wtforms.StringField(&amp;#39;Foo&amp;#39;)
    bar = wtforms.IntegerField(&amp;#39;Bar&amp;#39;)
    is_baz = wtforms.BooleanField(&amp;#39;IzBaz&amp;#39;)

fd = DummyMultiDict({&amp;#39;foo&amp;#39;: &amp;#39;ayy&amp;#39;})
f = FooForm(fd)

print(f.data)

# # # # #
class DummyMultiDict(dict):
    def getlist(self, key):
        v = self[key]
        return v if isinstance(v, (list, tuple)) else [v]
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The above produces:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;{'is_baz': False, 'foo': 'ayy', 'bar': None}
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This is not necessarily what you want when working with REST APIs or PATCH-like
requests. (Again, wtforms is not really meant for that). The default values your
code expects may be different from the default values wtforms assigns.&lt;/p&gt;

&lt;p&gt;Suppose you have:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;py&quot;&gt;def save(foo=&amp;#39;No name&amp;#39;, bar=42, is_baz=True):
    return db.save(Object(foo=foo, bar=bar, is_baz=is_baz))

fd = DummyMultiDict({&amp;#39;foo&amp;#39;: &amp;#39;ayy&amp;#39;})
f = Foo(fd)

save(**f.data)
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;In this case, you would expect a new entry in the “database” to be
&lt;code&gt;Object(foo='ayy', bar=42, is_baz=True)&lt;/code&gt;. But the actual entry saved is
 &lt;code&gt;Object(foo='ayy', bar=None, is_baz=False)&lt;/code&gt;.
 All your unit tests fail, your users are confused, and your manager is mad.&lt;/p&gt;

&lt;p&gt;Here is a small wrapper around &lt;code&gt;wtforms.Form&lt;/code&gt; to better handle the above problem. (There is also &lt;a href=&quot;https://github.com/kvesteri/wtforms-json&quot;&gt;wtforms-json&lt;/a&gt;,
but its interface is quite different and feels wrong.)&lt;/p&gt;

&lt;h2 id=&quot;jform&quot;&gt;JForm&lt;/h2&gt;

&lt;pre&gt;&lt;code class=&quot;py&quot;&gt;import wtforms


class JForm(wtforms.Form):

    def process(self, *args, **kwargs):
        if args:
            formdata = args[0]
        else:
            formdata = kwargs.get(&amp;#39;formdata&amp;#39;, None)
        self._formdata = formdata
        super(JForm, self).process(*args, **kwargs)

    @property
    def data(self):
        &amp;quot;&amp;quot;&amp;quot;Returns form data with fields that were not in request popped.&amp;quot;&amp;quot;&amp;quot;
        d = super(JForm, self).data
        if self._formdata is None:
            return d
        keys = d.keys()
        keys = keys if isinstance(keys, list) else list(keys)
        for k in keys:
            if k not in self._formdata:
                del d[k]
        return d
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;When &lt;code&gt;form.data&lt;/code&gt; is requested, &lt;code&gt;JForm&lt;/code&gt; ignores any property that was not
included in the original form creation.&lt;/p&gt;

&lt;h2 id=&quot;usage&quot;&gt;Usage:&lt;/h2&gt;

&lt;pre&gt;&lt;code class=&quot;py&quot;&gt;import wtforms

class MyBaseForm(JForm):
    pass

class FooForm(MyBaseForm):
    foo = wtforms.StringField(&amp;#39;Foo&amp;#39;)
    bar = wtforms.IntegerField(&amp;#39;Bar&amp;#39;)
    is_baz = wtforms.BooleanField(&amp;#39;IzBaz&amp;#39;)

fd = DummyMultiDict({&amp;#39;foo&amp;#39;: &amp;#39;ayy&amp;#39;})
f = Foo(fd)

print(f.data) # {&amp;#39;foo&amp;#39;: &amp;#39;ayy&amp;#39;}
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Happy coding. It also works nicely with other wrappers such as &lt;a href=&quot;https://github.com/lepture/flask-wtf&quot;&gt;flask-wtf&lt;/a&gt;. Simply change to&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;class MyBaseForm(JForm, flask_wtf.Form):
    pass
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Update: I did not want to publish this as a pip-package because … I is lazy.&lt;/p&gt;
</content>
				<published>2015-11-13 00:00:00 +0000</published>
				<url>https://bekt.net/p/wtforms-patch/</url>
				<guid isPermaLink="true">https://bekt.net/p/wtforms-patch/</guid>
			</item>
		
			<item>
				<title>Sharing AWS Credentials Between Users On a Docker Container</title>
				<excerpt>&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;:
AWS CLI configurations and credentials are stored in the user’s home directory by
default (&lt;code&gt;~/.aws&lt;/code&gt;). This becomes a problem when other users such as
&lt;code&gt;root&lt;/code&gt;, &lt;code&gt;www-data&lt;/code&gt;, &lt;code&gt;nobody&lt;/code&gt;, or cron jobs need access to these credentials.
This post shows how to get around this in a Docker environment.&lt;/p&gt;
</excerpt>
				<content>&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;:
AWS CLI configurations and credentials are stored in the user’s home directory by
default (&lt;code&gt;~/.aws&lt;/code&gt;). This becomes a problem when other users such as
&lt;code&gt;root&lt;/code&gt;, &lt;code&gt;www-data&lt;/code&gt;, &lt;code&gt;nobody&lt;/code&gt;, or cron jobs need access to these credentials.
This post shows how to get around this in a Docker environment.&lt;/p&gt;

&lt;p&gt;&lt;a href=&quot;https://www.docker.com/&quot;&gt;Docker&lt;/a&gt; is a great application containment tool for
building and shipping software of any type. You can learn more about Docker
&lt;a href=&quot;https://www.docker.com/whatisdocker&quot;&gt;here&lt;/a&gt;. We love and use Docker at
&lt;a href=&quot;https://www.humanlink.co&quot;&gt;Humanlink&lt;/a&gt; with
&lt;a href=&quot;http://aws.amazon.com/elasticbeanstalk/&quot;&gt;AWS Elastic Beanstalk&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Being on Elastic Beanstalk means utilizing other amazing Amazon services as well.
&lt;a href=&quot;http://aws.amazon.com/cli/&quot;&gt;AWS CLI&lt;/a&gt; and &lt;a href=&quot;https://github.com/boto/boto&quot;&gt;boto&lt;/a&gt;
(for Python developers) are the de-facto tools for interacting with AWS.&lt;/p&gt;

&lt;p&gt;There are a few ways to provide credentials to these tools.
On production, it is a good idea to serve them as environment
variables (such as &lt;code&gt;AWS_ACCESS_KEY_ID&lt;/code&gt; and &lt;code&gt;AWS_SECRET_ACCESS_KEY&lt;/code&gt;).
During development, however, it is recommended that these values are set via
the &lt;code&gt;aws configure&lt;/code&gt; command, which in turn places config files under &lt;code&gt;~/.aws/&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;I was planning on having a full-blown example with detailed explanations,
but that quickly became a long post and lost its focus.&lt;/p&gt;

&lt;p&gt;In short, we do not want to pollute the Dockerfile just for the development environment. When running the Docker image locally, we can mount the &lt;code&gt;~/.aws&lt;/code&gt; directory AND set the &lt;code&gt;$HOME&lt;/code&gt; environment variable. Otherwise, &lt;code&gt;$HOME&lt;/code&gt; defaults
to &lt;code&gt;/root&lt;/code&gt; which causes permission problems for non-root users.&lt;/p&gt;

&lt;p&gt;Since mounted file permissions are copied over to the Docker container, we
need to give read permissions to everyone (on your host machine).&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;$ chmod 644 ~/.aws/*
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;We can now run the container:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;$ docker run -it --rm \
  -e &amp;quot;HOME=/home&amp;quot; \
  -v $HOME/.aws:/home/.aws \
  myapp
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Now the credentials are available system-wide in the Docker container for any
user to use and communicate with AWS.&lt;/p&gt;
</content>
				<published>2015-07-18 00:00:00 +0000</published>
				<url>https://bekt.net/p/docker-aws-credentials/</url>
				<guid isPermaLink="true">https://bekt.net/p/docker-aws-credentials/</guid>
			</item>
		
			<item>
				<title>Automatically Download the Latest App Engine SDK</title>
				<excerpt>&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;:
Google doesn’t provide a permanent link to the latest SDK;
update check endpoint is not reliable;
I provide a snippet (&lt;a href=&quot;https://gist.github.com/Bekt/7cb68b12674b282c8d78&quot;&gt;view&lt;/a&gt;)
to work around this.&lt;/p&gt;
</excerpt>
				<content>&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;:
Google doesn’t provide a permanent link to the latest SDK;
update check endpoint is not reliable;
I provide a snippet (&lt;a href=&quot;https://gist.github.com/Bekt/7cb68b12674b282c8d78&quot;&gt;view&lt;/a&gt;)
to work around this.&lt;/p&gt;

&lt;p&gt;Google provides an SDK for interacting with App Engine. &lt;code&gt;dev_appserver.py&lt;/code&gt;
simulates the App Engine Python runtime environment locally.
&lt;code&gt;appcfg.py&lt;/code&gt; is used to interact with App Engine to do tasks such as deploying
a new version of the application.&lt;/p&gt;

&lt;p&gt;For continuous deployment / integration scripts such as those for
&lt;a href=&quot;https://circleci.com/docs/deploy-google-app-engine&quot;&gt;CircleCI&lt;/a&gt;,
&lt;a href=&quot;https://github.com/travis-ci/dpl/issues/94&quot;&gt;Travis CI&lt;/a&gt;,
or &lt;a href=&quot;https://jenkins-ci.org&quot;&gt;Jenkins CI&lt;/a&gt;, it is usually necessary to download
the latest version of the Google App Engine SDK. Unfortunately, Google does not
provide a permanent link to the latest version for easy download.
It seems like a basic need. I talk about how to programatically get the latest
SDK in this post.&lt;/p&gt;

&lt;h2 id=&quot;updatecheck-endpoint&quot;&gt;UpdateCheck Endpoint&lt;/h2&gt;

&lt;p&gt;In &lt;code&gt;appengine/tools/sdk_update_checker.py&lt;/code&gt;, I found the API endpoint for
checking for updates to the SDK: &lt;code&gt;https://appengine.google.com/api/updatecheck&lt;/code&gt;.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;$ curl https://appengine.google.com/api/updatecheck

release: &amp;quot;1.9.19&amp;quot;
timestamp: 1424415497
api_versions: [&amp;#39;1&amp;#39;]
supported_api_versions:
  python:
    api_versions: [&amp;#39;1&amp;#39;]
  python27:
    api_versions: [&amp;#39;1&amp;#39;]
  go:
    api_versions: [&amp;#39;go1&amp;#39;]
  java7:
    api_versions: [&amp;#39;1.0&amp;#39;]
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Great, this is all we need. Not so fast! But it is useful.&lt;/p&gt;

&lt;h2 id=&quot;sdk-download-url&quot;&gt;SDK Download URL&lt;/h2&gt;

&lt;p&gt;On the App Engine SDK &lt;a href=&quot;https://cloud.google.com/appengine/downloads&quot;&gt;downloads&lt;/a&gt;,
the only link to the latest SDK is something like:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;https://storage.googleapis.com/appengine-sdks/featured/google_appengine_1.9.20.zip&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Notice the version number is 1.9.20, not 1.9.19.&lt;/p&gt;

&lt;p&gt;Using the Google Cloud Storage API, we can list all the files in the
&lt;code&gt;appengine-sdks/featured&lt;/code&gt; bucket:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;https://www.googleapis.com/storage/v1/b/appengine-sdks/o?prefix=featured&lt;/code&gt;&lt;/p&gt;

&lt;h2 id=&quot;fetch-the-latest-sdk&quot;&gt;Fetch the Latest SDK&lt;/h2&gt;

&lt;p&gt;Given the two points from above, we can can automatically check for the latest SDK
version and download the zip with that version.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;# script.bash
# DON&amp;#39;T COPY-PASTE, READ BELOW.

#!/usr/bin/env bash

API_CHECK=https://appengine.google.com/api/updatecheck
SDK_VERSION=$(curl -s $API_CHECK | awk -F &amp;#39;\&amp;quot;&amp;#39; &amp;#39;/release/ {print $2}&amp;#39;)
SDK_URL=https://storage.googleapis.com/appengine-sdks/featured/google_appengine_$SDK_VERSION.zip

function download_sdk {
  echo &amp;quot;&amp;gt;&amp;gt;&amp;gt; Downloading...&amp;quot;
  curl -fo $HOME/gae.zip $SDK_URL || exit 1
  unzip -qd $HOME $HOME/gae.zip
}

function upload {
  $HOME/google_appengine/appcfg.py \
      --oauth2 update my-app
}

download_sdk
upload
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Easy, right? Ehhhh.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;./script.bash

&amp;gt;&amp;gt;&amp;gt; Downloading...
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0

curl: (22) The requested URL returned error: 404 Not Found
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Apparently, the UpdateCheck endpoint does not always have the latest
version. Like wut. From my experience, it can take anywhere from 1-7 days for the
endpoint to return the latest version.
Additionally, once a new version becomes available,
previous download links become unavailable. The App Engine team acknowledged the &lt;a href=&quot;https://code.google.com/p/googleappengine/issues/detail?id=11604&quot;&gt;issue&lt;/a&gt;
five months ago but still has not addressed it.&lt;/p&gt;

&lt;h2 id=&quot;revisiting-sdk-download-url&quot;&gt;Revisiting SDK Download URL&lt;/h2&gt;

&lt;p&gt;Well, obviously at this point the only way to get the latest SDK version is to
parse the HTML content of the download page. We could also look through all
the files in the &lt;code&gt;featured&lt;/code&gt; bucket and find the one correct file to download.
However, nobody should do that!
Since we don’t necessarily need the latest version to simply deploy the project,
we can fallback to a slightly older SDK version (the one UpdateCheck returns).&lt;/p&gt;

&lt;p&gt;As indicated on the downloads page, deprecated SDK downloads can be found at
the following link:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;https://console.developers.google.com/m/cloudstorage/b/appengine-sdks/o/deprecated/1919/google_appengine_1.9.19.zip&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;which I found out is the same as:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;https://storage.googleapis.com/appengine-sdks/deprecated/1919/google_appengine_1.9.19.zip&lt;/code&gt;&lt;/p&gt;

&lt;h2 id=&quot;new-scriptbash&quot;&gt;New script.bash&lt;/h2&gt;

&lt;p&gt;So now we can write a script that fall-backs to the deprecated SDK URL if the first
URL does not work.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;# script.bash

#!/usr/bin/env bash

API_CHECK=https://appengine.google.com/api/updatecheck
SDK_VERSION=$(curl -s $API_CHECK | awk -F &amp;#39;\&amp;quot;&amp;#39; &amp;#39;/release/ {print $2}&amp;#39;)
# Remove the dots.
SDK_VERSION_S=${SDK_VERSION//./}

SDK_URL=https://storage.googleapis.com/appengine-sdks/
SDK_URL_A=&amp;quot;${SDK_URL}featured/google_appengine_${SDK_VERSION}.zip&amp;quot;
SDK_URL_B=&amp;quot;${SDK_URL}deprecated/$SDK_VERSION_S/google_appengine_${SDK_VERSION}.zip&amp;quot;

function download_sdk {
  echo &amp;quot;&amp;gt;&amp;gt;&amp;gt; Downloading...&amp;quot;
  curl -fo $HOME/gae.zip $SDK_URL_A || \
      curl -fo $HOME/gae.zip $SDK_URL_B || \
      exit 1
  unzip -qd $HOME $HOME/gae.zip
}

function upload {
  echo &amp;quot;&amp;gt;&amp;gt;&amp;gt; Deploying...&amp;quot;
  $HOME/google_appengine/appcfg.py \
      --oauth2 update my-app
}

download_sdk
upload
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;If we run the script again, it works as expected:&lt;/p&gt;
&lt;ul&gt;
  &lt;li&gt;Tries to download from the &lt;code&gt;features&lt;/code&gt; folder first&lt;/li&gt;
  &lt;li&gt;Otherwise, tries to download from the &lt;code&gt;deprecated&lt;/code&gt; folder&lt;/li&gt;
&lt;/ul&gt;

&lt;h2 id=&quot;conclusion&quot;&gt;Conclusion&lt;/h2&gt;

&lt;p&gt;We came up with &lt;code&gt;script.bash&lt;/code&gt; that automatically downloads the “latest”
Google App Engine Python/PHP SDK to make life easier. This is especially useful
during automated builds and deployments.&lt;/p&gt;

&lt;h3 id=&quot;references&quot;&gt;References&lt;/h3&gt;
&lt;p&gt;0: https://code.google.com/p/googleappengine/issues/detail?id=11604&lt;/p&gt;
</content>
				<published>2015-05-20 00:00:00 +0000</published>
				<url>https://bekt.net/p/gae-sdk/</url>
				<guid isPermaLink="true">https://bekt.net/p/gae-sdk/</guid>
			</item>
		
			<item>
				<title>App Engine and SSL</title>
				<excerpt>&lt;p&gt;Google App Engine is a great platform for getting things done quickly.
However, it can be very unpleasant to work with due to its sandboxed environment
and close source code. Basic needs such as installing third-party
libraries can be tricky to install as well.&lt;/p&gt;
</excerpt>
				<content>&lt;p&gt;Google App Engine is a great platform for getting things done quickly.
However, it can be very unpleasant to work with due to its sandboxed environment
and close source code. Basic needs such as installing third-party
libraries can be tricky to install as well.&lt;/p&gt;

&lt;p&gt;Getting one of the most
popular python libraries, &lt;a href=&quot;http://docs.python-requests.org/en/latest/&quot;&gt;python-requests&lt;/a&gt;,
was particularly tricky to get it running and working with SSL connections.
I’ll walk through how I fixed the issue.&lt;/p&gt;

&lt;p&gt;Start by adding the library to the project:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;bash&quot;&gt;# From project root.
pip install -t lib/ requests
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The above command pip-installs the &lt;code&gt;requests&lt;/code&gt; library into the &lt;code&gt;lib&lt;/code&gt;
directory. This is where all the third-party libraries can be placed.&lt;/p&gt;

&lt;p&gt;Now we need to let App Engine know about this. Create or modify the file
&lt;code&gt;appengine_config.py&lt;/code&gt; in the root of the project.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;python&quot;&gt;from google.appengine.ext import vendor
vendor.add(&amp;#39;lib&amp;#39;)
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;&lt;code&gt;appengine_config.py&lt;/code&gt; runs when a new instance is created. &lt;code&gt;vendor.add&lt;/code&gt; adds the specified path to &lt;code&gt;$PYTHONPATH&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;At this point, most third-party libraries work just fine. However,
there’s a bit of work that needs to be done to get &lt;code&gt;requests&lt;/code&gt; working.&lt;/p&gt;

&lt;p&gt;Head over to http://localhost:8000/console and execute:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;python&quot;&gt;import requests

r = requests.get(&amp;#39;https://httpbin.org/status/200&amp;#39;)
print(r.status_code)
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;In a normal Python environment, the code executes just fine printing a
200 status. But on GAE, the following exception occurs:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;python&quot;&gt;Traceback (most recent call last):
  File
&amp;quot;/Applications/GoogleAppEngineLauncher.app/Contents/Resources/GoogleAppEngine-default.bundle/Contents/Resources/google_appengine/google/appengine/tools/devappserver2/python/request_handler.py&amp;quot;,
line 225, in handle_interactive_request
    exec(compiled_code, self._command_globals)
  File &amp;quot;&amp;lt;string&amp;gt;&amp;quot;, line 1, in &amp;lt;module&amp;gt;
  File &amp;quot;.../lib/requests/__init__.py&amp;quot;, line 58, in &amp;lt;module&amp;gt;
    from . import utils
  File &amp;quot;.../lib/requests/utils.py&amp;quot;, line 26, in &amp;lt;module&amp;gt;
    from .compat import parse_http_list as _parse_list_header
  File &amp;quot;.../lib/requests/compat.py&amp;quot;, line 42, in &amp;lt;module&amp;gt;
    from .packages.urllib3.packages.ordered_dict import OrderedDict
  File &amp;quot;.../lib/requests/packages/__init__.py&amp;quot;, line 95, in load_module
    raise ImportError(&amp;quot;No module named &amp;#39;%s&amp;#39;&amp;quot; % (name,))
ImportError: No module named &amp;#39;requests.packages.urllib3&amp;#39;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The issue goes away once the
&lt;a href=&quot;https://cloud.google.com/appengine/docs/python/sockets/ssl_support&quot;&gt;ssl&lt;/a&gt; library is included in &lt;code&gt;app.yaml&lt;/code&gt;:&lt;/p&gt;

&lt;pre&gt;
&lt;code class=&quot;nohighlight&quot;&gt;libraries:
- name: ssl
  version: latest
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;But wait, there’s more! The code should now work remotely.
However, it still doesn’t work on the development server.&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;python&quot;&gt;Traceback (most recent call last):
  File &amp;quot;/Applications/GoogleAppEngineLauncher.app/Contents/Resources/GoogleAppEngine-default.bundle/Contents/Resources/google_appengine/google/appengine/tools/devappserver2/python/request_handler.py&amp;quot;, line 225, in handle_interactive_request
    exec(compiled_code, self._command_globals)
  File &amp;quot;&amp;lt;string&amp;gt;&amp;quot;, line 3, in &amp;lt;module&amp;gt;
  File &amp;quot;.../lib/requests/api.py&amp;quot;, line 68, in get
    return request(&amp;#39;get&amp;#39;, url, **kwargs)
  File &amp;quot;.../lib/requests/api.py&amp;quot;, line 50, in request
    response = session.request(method=method, url=url, **kwargs)
  [...]
  File &amp;quot;/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/ssl.py&amp;quot;, line 387, in wrap_socket
    ciphers=ciphers)
  File &amp;quot;/System/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/ssl.py&amp;quot;, line 141, in __init__
    ciphers)
TypeError: must be _socket.socket, not socket
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The problem is GAE has a “whitelist” of select standard libraries.
SSL (_ssl, _socket) is not one of them.
So, we need to tweak the sandbox environment (dangerous) carefully.
The below code uses the standard Python socket library instead of the GAE-provided
in the development environment. Modify &lt;code&gt;appengine_config.py&lt;/code&gt;:&lt;/p&gt;

&lt;pre&gt;&lt;code class=&quot;python&quot;&gt;import os

# Workaround the dev-environment SSL
#   http://stackoverflow.com/q/16192916/893652
if os.environ.get(&amp;#39;SERVER_SOFTWARE&amp;#39;, &amp;#39;&amp;#39;).startswith(&amp;#39;Development&amp;#39;):
    import imp
    import os.path
    from google.appengine.tools.devappserver2.python import sandbox

    sandbox._WHITE_LIST_C_MODULES += [&amp;#39;_ssl&amp;#39;, &amp;#39;_socket&amp;#39;]
    # Use the system socket.
    psocket = os.path.join(os.path.dirname(os.__file__), &amp;#39;socket.py&amp;#39;)
    imp.load_source(&amp;#39;socket&amp;#39;, psocket)
&lt;/code&gt;&lt;/pre&gt;

&lt;pre&gt;&lt;code class=&quot;nohighlight&quot;&gt;INFO     2015-04-04 06:57:28,449 module.py:737] default: &amp;quot;POST / HTTP/1.1&amp;quot; 200 4
INFO     2015-04-04 06:57:46,868 connectionpool.py:735] Starting new HTTPS connection
    (1): httpbin.org
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This solution mostly works, except for non-blocking sockets.
I haven’t had a need for that yet :)&lt;/p&gt;

&lt;h3 id=&quot;references&quot;&gt;References&lt;/h3&gt;
&lt;p&gt;0: &lt;a href=&quot;https://code.google.com/p/googleappengine/issues/detail?id=9246&quot;&gt;Open issue that is 2 years old&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;1: http://stackoverflow.com/q/16192916/893652&lt;/p&gt;
</content>
				<published>2015-04-05 00:00:00 +0000</published>
				<url>https://bekt.net/p/gae-ssl/</url>
				<guid isPermaLink="true">https://bekt.net/p/gae-ssl/</guid>
			</item>
		
	</channel>
</rss>
