Browse Source

Merge remote-tracking branch 'grafana/master' into influx-db-query2

ryan 8 years ago
parent
commit
6ee886cd6a
100 changed files with 1473 additions and 1780 deletions
  1. 3 2
      CHANGELOG.md
  2. 5 1
      conf/defaults.ini
  3. 5 1
      conf/sample.ini
  4. 11 10
      docs/Makefile
  5. 1 1
      docs/VERSION
  6. 4 7
      docs/sources/archive.md
  7. 1 0
      docs/sources/features/panels/dashlist.md
  8. 23 18
      docs/sources/features/panels/graph.md
  9. 1 0
      docs/sources/features/panels/singlestat.md
  10. 1 0
      docs/sources/features/panels/table_panel.md
  11. 0 4
      docs/sources/http_api/dashboard.md
  12. 3 1
      docs/sources/installation/configuration.md
  13. 6 7
      emails/templates/layouts/default.html
  14. 3 0
      pkg/api/alerting.go
  15. 1 1
      pkg/api/datasources.go
  16. 17 1
      pkg/api/dtos/models.go
  17. 39 1
      pkg/api/http_server.go
  18. 2 4
      pkg/api/login.go
  19. 6 1
      pkg/api/pluginproxy/pluginproxy_test.go
  20. 2 1
      pkg/components/imguploader/imguploader.go
  21. 1 1
      pkg/components/imguploader/s3uploader_test.go
  22. 17 8
      pkg/components/imguploader/webdavuploader.go
  23. 11 2
      pkg/components/imguploader/webdavuploader_test.go
  24. 13 2
      pkg/components/securejsondata/securejsondata.go
  25. 4 2
      pkg/log/log.go
  26. 8 3
      pkg/models/datasource_cache_test.go
  27. 3 0
      pkg/models/health.go
  28. 1 0
      pkg/models/notifications.go
  29. 1 1
      pkg/services/notifications/mailer.go
  30. 14 0
      pkg/services/sqlstore/health.go
  31. 6 1
      pkg/services/sqlstore/plugin_setting.go
  32. 1 0
      pkg/services/sqlstore/sqlstore.go
  33. 7 1
      pkg/setting/setting.go
  34. 6 5
      pkg/social/social.go
  35. 4 9
      pkg/tsdb/influxdb/query.go
  36. 9 10
      pkg/util/encryption.go
  37. 4 2
      pkg/util/encryption_test.go
  38. 12 0
      pkg/util/strings.go
  39. 11 0
      pkg/util/strings_test.go
  40. 12 1
      public/app/core/time_series2.ts
  41. 7 0
      public/app/features/annotations/annotations_srv.ts
  42. 1 1
      public/app/features/annotations/event_manager.ts
  43. 3 3
      public/app/features/annotations/partials/editor.html
  44. 1 0
      public/app/features/dashboard/shareSnapshotCtrl.js
  45. 1 1
      public/app/plugins/datasource/influxdb/influx_query.ts
  46. 53 13
      public/app/plugins/datasource/prometheus/datasource.ts
  47. 4 0
      public/app/plugins/datasource/prometheus/partials/query.editor.html
  48. 14 1
      public/app/plugins/datasource/prometheus/query_ctrl.ts
  49. 24 0
      public/app/plugins/datasource/prometheus/specs/datasource_specs.ts
  50. 10 1
      public/app/plugins/panel/graph/graph.ts
  51. 6 0
      public/app/plugins/panel/graph/module.ts
  52. 1 0
      public/app/plugins/panel/graph/series_overrides_ctrl.js
  53. 14 0
      public/app/plugins/panel/graph/specs/graph_specs.ts
  54. 1 1
      public/app/plugins/panel/graph/tab_display.html
  55. 2 2
      public/app/plugins/panel/heatmap/axes_editor.ts
  56. 2 1
      public/app/system.conf.js
  57. 3 0
      public/dashboards/default.json
  58. 3 0
      public/dashboards/template_vars.json
  59. 87 89
      public/emails/alert_notification.html
  60. 57 59
      public/emails/invited_to_org.html
  61. 59 61
      public/emails/new_user_invite.html
  62. 53 55
      public/emails/reset_password.html
  63. 56 58
      public/emails/signup_started.html
  64. 56 58
      public/emails/welcome_on_signup.html
  65. 15 3
      public/sass/pages/_alerting.scss
  66. 3 3
      public/sass/pages/_dashboard.scss
  67. 1 0
      public/test/test-main.js
  68. 236 0
      public/vendor/flot/jquery.flot.dashes.js
  69. 0 24
      vendor/github.com/Unknwon/com/.gitignore
  70. 4 8
      vendor/github.com/Unknwon/com/README.md
  71. 0 140
      vendor/github.com/Unknwon/com/cmd_test.go
  72. 1 1
      vendor/github.com/Unknwon/com/convert.go
  73. 0 56
      vendor/github.com/Unknwon/com/convert_test.go
  74. 0 58
      vendor/github.com/Unknwon/com/dir_test.go
  75. 0 299
      vendor/github.com/Unknwon/com/example_test.go
  76. 0 61
      vendor/github.com/Unknwon/com/file_test.go
  77. 0 35
      vendor/github.com/Unknwon/com/html_test.go
  78. 0 111
      vendor/github.com/Unknwon/com/http_test.go
  79. 10 5
      vendor/github.com/Unknwon/com/math.go
  80. 3 3
      vendor/github.com/Unknwon/com/path.go
  81. 0 67
      vendor/github.com/Unknwon/com/path_test.go
  82. 0 70
      vendor/github.com/Unknwon/com/regex_test.go
  83. 0 99
      vendor/github.com/Unknwon/com/slice_test.go
  84. 134 21
      vendor/github.com/Unknwon/com/string.go
  85. 0 82
      vendor/github.com/Unknwon/com/string_test.go
  86. 0 14
      vendor/github.com/go-macaron/binding/.travis.yml
  87. 28 22
      vendor/github.com/go-macaron/binding/binding.go
  88. 0 14
      vendor/github.com/go-macaron/inject/.travis.yml
  89. 68 8
      vendor/github.com/go-macaron/inject/inject.go
  90. 0 2
      vendor/github.com/go-macaron/session/.gitignore
  91. 0 14
      vendor/github.com/go-macaron/session/.travis.yml
  92. 2 2
      vendor/github.com/go-macaron/session/README.md
  93. 6 6
      vendor/github.com/go-macaron/session/file.go
  94. 27 0
      vendor/golang.org/x/crypto/LICENSE
  95. 22 0
      vendor/golang.org/x/crypto/PATENTS
  96. 77 0
      vendor/golang.org/x/crypto/pbkdf2/pbkdf2.go
  97. 0 2
      vendor/gopkg.in/macaron.v1/.gitignore
  98. 0 13
      vendor/gopkg.in/macaron.v1/.travis.yml
  99. 6 8
      vendor/gopkg.in/macaron.v1/README.md
  100. 33 16
      vendor/gopkg.in/macaron.v1/context.go

+ 3 - 2
CHANGELOG.md

@@ -7,8 +7,7 @@
 * **Panels**: Delay loading & Lazy load panels as they become visible (scrolled into view) [#5216](https://github.com/grafana/grafana/issues/5216) thx [@jifwin](https://github.com/jifwin)
 * **Panels**: Delay loading & Lazy load panels as they become visible (scrolled into view) [#5216](https://github.com/grafana/grafana/issues/5216) thx [@jifwin](https://github.com/jifwin)
 * **Graph**: Support auto grid min/max when using log scale [#3090](https://github.com/grafana/grafana/issues/3090), thx [@bigbenhur](https://github.com/bigbenhur)
 * **Graph**: Support auto grid min/max when using log scale [#3090](https://github.com/grafana/grafana/issues/3090), thx [@bigbenhur](https://github.com/bigbenhur)
 * **Graph**: Support for histograms [#600](https://github.com/grafana/grafana/issues/600)
 * **Graph**: Support for histograms [#600](https://github.com/grafana/grafana/issues/600)
-* **Elasticsearch**: Support histogram aggregations [#3164](https://github.com/grafana/grafana/issues/3164)
-
+* **Prometheus**: Support table response formats (column per label) [#6140](https://github.com/grafana/grafana/issues/6140), thx [@mtanda](https://github.com/mtanda)
 
 
 ## Minor Enchancements
 ## Minor Enchancements
 
 
@@ -20,10 +19,12 @@
 * **Oauth**: Add common type for oauth authorization errors [#6428](https://github.com/grafana/grafana/issues/6428) thx [@amenzhinsky](https://github.com/amenzhinsky)
 * **Oauth**: Add common type for oauth authorization errors [#6428](https://github.com/grafana/grafana/issues/6428) thx [@amenzhinsky](https://github.com/amenzhinsky)
 * **Templating**: Data source variable now supports multi value and panel repeats [#7030](https://github.com/grafana/grafana/issues/7030) thx [@mtanda](https://github.com/mtanda)
 * **Templating**: Data source variable now supports multi value and panel repeats [#7030](https://github.com/grafana/grafana/issues/7030) thx [@mtanda](https://github.com/mtanda)
 * **Telegram**: Telegram alert is not sending metric and legend. [#8110](https://github.com/grafana/grafana/issues/8110), thx [@bashgeek](https://github.com/bashgeek)
 * **Telegram**: Telegram alert is not sending metric and legend. [#8110](https://github.com/grafana/grafana/issues/8110), thx [@bashgeek](https://github.com/bashgeek)
+* **Graph**: Support dashed lines [#514](https://github.com/grafana/grafana/issues/514), thx [@smalik03](https://github.com/smalik03)
 
 
 ## Fixes
 ## Fixes
 * **Table Panel**: Fixed annotation display in table panel, [#8023](https://github.com/grafana/grafana/issues/8023)
 * **Table Panel**: Fixed annotation display in table panel, [#8023](https://github.com/grafana/grafana/issues/8023)
 * **Dashboard**: If refresh is blocked due to tab not visible, then refresh when it becomes visible [#8076](https://github.com/grafana/grafana/issues/8076) thanks [@SimenB](https://github.com/SimenB)
 * **Dashboard**: If refresh is blocked due to tab not visible, then refresh when it becomes visible [#8076](https://github.com/grafana/grafana/issues/8076) thanks [@SimenB](https://github.com/SimenB)
+* **Snapshots**: Fixed problem with annotations & snapshots [#7659](https://github.com/grafana/grafana/issues/7659)
 
 
 # 4.2.0 (2017-03-22)
 # 4.2.0 (2017-03-22)
 ## Minor Enhancements
 ## Minor Enhancements

+ 5 - 1
conf/defaults.ini

@@ -25,7 +25,7 @@ plugins = data/plugins
 
 
 #################################### Server ##############################
 #################################### Server ##############################
 [server]
 [server]
-# Protocol (http or https)
+# Protocol (http, https, socket)
 protocol = http
 protocol = http
 
 
 # The ip address to bind to, empty will bind to all interfaces
 # The ip address to bind to, empty will bind to all interfaces
@@ -57,6 +57,9 @@ enable_gzip = false
 cert_file =
 cert_file =
 cert_key =
 cert_key =
 
 
+# Unix socket path
+socket = /tmp/grafana.sock
+
 #################################### Database ############################
 #################################### Database ############################
 [database]
 [database]
 # You can configure the database connection by specifying type, host, name, user and password
 # You can configure the database connection by specifying type, host, name, user and password
@@ -444,3 +447,4 @@ secret_key =
 url =
 url =
 username =
 username =
 password =
 password =
+public_url =

+ 5 - 1
conf/sample.ini

@@ -26,7 +26,7 @@
 #
 #
 #################################### Server ####################################
 #################################### Server ####################################
 [server]
 [server]
-# Protocol (http or https)
+# Protocol (http, https, socket)
 ;protocol = http
 ;protocol = http
 
 
 # The ip address to bind to, empty will bind to all interfaces
 # The ip address to bind to, empty will bind to all interfaces
@@ -59,6 +59,9 @@
 ;cert_file =
 ;cert_file =
 ;cert_key =
 ;cert_key =
 
 
+# Unix socket path
+;socket =
+
 #################################### Database ####################################
 #################################### Database ####################################
 [database]
 [database]
 # You can configure the database connection by specifying type, host, name, user and password
 # You can configure the database connection by specifying type, host, name, user and password
@@ -399,5 +402,6 @@
 
 
 [external_image_storage.webdav]
 [external_image_storage.webdav]
 ;url =
 ;url =
+;public_url =
 ;username =
 ;username =
 ;password =
 ;password =

+ 11 - 10
docs/Makefile

@@ -1,4 +1,4 @@
-.PHONY: all default docs docs-build docs-shell shell test
+.PHONY: all default docs docs-build docs-shell shell checkvars
 
 
 # to allow `make DOCSPORT=9000 docs`
 # to allow `make DOCSPORT=9000 docs`
 DOCSPORT := 3004
 DOCSPORT := 3004
@@ -11,23 +11,24 @@ DOCS_MOUNT := -v $(SOURCES_HOST_DIR):/site/content
 
 
 DOCKER_RUN_DOCS := docker run --rm -it $(DOCS_MOUNT) -e NOCACHE -p 3004:3004 -p 3005:3005
 DOCKER_RUN_DOCS := docker run --rm -it $(DOCS_MOUNT) -e NOCACHE -p 3004:3004 -p 3005:3005
 
 
+VERSION := $(shell head -n 1 VERSION)
 
 
 default: docs
 default: docs
 
 
+checkvars:
+ifndef ENV
+	$(error ENV is undefined set via ENV=staging or ENV=prod as argument to make)
+endif
+
 docs: docs-build
 docs: docs-build
 	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "grunt --env=dev-docs && grunt connect --port=3004"
 	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "grunt --env=dev-docs && grunt connect --port=3004"
 
 
-test: docs-build
-	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "ls -la /site/content"
-
-docs-watch: docs-build
+watch: docs-build
 	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "grunt --env=dev-docs && grunt connect --port=3004 & grunt watch --port=3004 --env=dev-docs"
 	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "grunt --env=dev-docs && grunt connect --port=3004 & grunt watch --port=3004 --env=dev-docs"
 
 
-publish: docs-build
-	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "./publish.sh staging-docs root"
-
-publish-prod: docs-build
-	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "./publish.sh prod-docs root"
+publish: checkvars docs-build
+	$(info Publishing ENV=${ENV} and VERSION=${VERSION})
+	$(DOCKER_RUN_DOCS) $(DOCS_MOUNT) -e DOCKERHOST "$(DOCKER_DOCS_IMAGE)" /bin/bash -c "./publish.sh ${ENV}-docs ${VERSION}"
 
 
 docs-build:
 docs-build:
 	docker build -t "$(DOCKER_DOCS_IMAGE)" --no-cache .
 	docker build -t "$(DOCKER_DOCS_IMAGE)" --no-cache .

+ 1 - 1
docs/VERSION

@@ -1 +1 @@
-3.1.0
+v4.2

+ 4 - 7
docs/sources/archive.md

@@ -12,10 +12,7 @@ weight = 200
 Here you can find links to older versions of the documentation that might be better suited for your version
 Here you can find links to older versions of the documentation that might be better suited for your version
 of Grafana.
 of Grafana.
 
 
-- [Latest](/)
-- [Version 3.1](/v3.1)
-- [Version 3.0](/v3.0)
-- [Version 2.6](/v2.6)
-- [Version 2.5](/v2.5)
-- [Version 2.1](/v2.1)
-- [Version 2.0](/v2.0)
+- [Latest](http://docs.grafana.org)
+- [Version 4.2](http://docs.grafana.org/v4.2)
+- [Version 3.1](http://docs.grafana.org/v3.1)
+- [Version 3.0](http://docs.grafana.org/v3.0)

+ 1 - 0
docs/sources/features/panels/dashlist.md

@@ -2,6 +2,7 @@
 title = "Dashboard List"
 title = "Dashboard List"
 keywords = ["grafana", "dashboard list", "documentation", "panel", "dashlist"]
 keywords = ["grafana", "dashboard list", "documentation", "panel", "dashlist"]
 type = "docs"
 type = "docs"
+aliases = ["/reference/dashlist/"]
 [menu.docs]
 [menu.docs]
 name = "Dashboard list"
 name = "Dashboard list"
 parent = "panels"
 parent = "panels"

+ 23 - 18
docs/sources/features/panels/graph.md

@@ -2,6 +2,7 @@
 title = "Graph Panel"
 title = "Graph Panel"
 keywords = ["grafana", "graph panel", "documentation", "guide", "graph"]
 keywords = ["grafana", "graph panel", "documentation", "guide", "graph"]
 type = "docs"
 type = "docs"
+aliases = ["/reference/graph/"]
 [menu.docs]
 [menu.docs]
 name = "Graph"
 name = "Graph"
 parent = "panels"
 parent = "panels"
@@ -18,7 +19,8 @@ Clicking the title for a panel exposes a menu.  The `edit` option opens addition
 options for the panel.
 options for the panel.
 
 
 ## General
 ## General
-![](/img/docs/v2/graph_general.png)
+
+![](/img/docs/v43/graph_general.png)
 
 
 The general tab allows customization of a panel's appearance and menu options.
 The general tab allows customization of a panel's appearance and menu options.
 
 
@@ -31,14 +33,14 @@ The general tab allows customization of a panel's appearance and menu options.
 ### Drilldown / detail link
 ### Drilldown / detail link
 
 
 The drilldown section allows adding dynamic links to the panel that can link to other dashboards
 The drilldown section allows adding dynamic links to the panel that can link to other dashboards
-or URLs
+or URLs.
 
 
 Each link has a title, a type and params.  A link can be either a ``dashboard`` or ``absolute`` links.
 Each link has a title, a type and params.  A link can be either a ``dashboard`` or ``absolute`` links.
-If it is a dashboard links, the `dashboard` value must be the name of a dashboard.  If it's an
-`absolute` link, the URL is the URL to link.
+If it is a dashboard link, the `dashboard` value must be the name of a dashboard.  If it is an
+`absolute` link, the URL is the URL to the link.
 
 
 ``params`` allows adding additional URL params to the links.  The format is the ``name=value`` with
 ``params`` allows adding additional URL params to the links.  The format is the ``name=value`` with
-multiple params separate by ``&``.  Template variables can be added as values using ``$myvar``.
+multiple params separated by ``&``.  Template variables can be added as values using ``$myvar``.
 
 
 When linking to another dashboard that uses template variables, you can use ``var-myvar=value`` to
 When linking to another dashboard that uses template variables, you can use ``var-myvar=value`` to
 populate the template variable to a desired value from the link.
 populate the template variable to a desired value from the link.
@@ -50,7 +52,7 @@ options.
 
 
 ## Axes & Grid
 ## Axes & Grid
 
 
-![](/img/docs/v2/graph_axes_grid_options.png)
+![](/img/docs/v43/graph_axes_grid_options.png)
 
 
 The Axes & Grid tab controls the display of axes, grids and legend.
 The Axes & Grid tab controls the display of axes, grids and legend.
 
 
@@ -74,7 +76,6 @@ values can be hidden from the legend using the ``Hide empty`` checkbox.
 ### Legend Values
 ### Legend Values
 
 
 Additional values can be shown along-side the legend names:
 Additional values can be shown along-side the legend names:
-
 - ``Total`` - Sum of all values returned from metric query
 - ``Total`` - Sum of all values returned from metric query
 - ``Current`` - Last value returned from the metric query
 - ``Current`` - Last value returned from the metric query
 - ``Min`` - Minimum of all values returned from metric query
 - ``Min`` - Minimum of all values returned from metric query
@@ -83,16 +84,16 @@ Additional values can be shown along-side the legend names:
 - ``Decimals`` - Controls how many decimals are displayed for legend values (and graph hover tooltips)
 - ``Decimals`` - Controls how many decimals are displayed for legend values (and graph hover tooltips)
 
 
 The legend values are calculated client side by Grafana and depend on what type of
 The legend values are calculated client side by Grafana and depend on what type of
-aggregation or point consolidation you metric query is using. All the above legend values cannot
+aggregation or point consolidation your metric query is using. All the above legend values cannot
 be correct at the same time. For example if you plot a rate like requests/second, this is probably
 be correct at the same time. For example if you plot a rate like requests/second, this is probably
 using average as aggregator, then the Total in the legend will not represent the total number of requests.
 using average as aggregator, then the Total in the legend will not represent the total number of requests.
 It is just the sum of all data points received by Grafana.
 It is just the sum of all data points received by Grafana.
 
 
 ## Display styles
 ## Display styles
 
 
-![](/img/docs/v2/graph_display_styles.png)
+![](/img/docs/v43/graph_display_styles.png)
 
 
-Display styles controls properties of the graph.
+Display styles control visual properties of the graph.
 
 
 ### Thresholds
 ### Thresholds
 
 
@@ -108,19 +109,19 @@ the graph crosses a particular threshold.
 
 
 ### Line Options
 ### Line Options
 
 
-- ``Line Fill`` - Amount of color fill for a series.  0 is none.
+- ``Line Fill`` - Amount of color fill for a series. 0 is none.
 - ``Line Width`` - The width of the line for a series.
 - ``Line Width`` - The width of the line for a series.
 - ``Null point mode`` - How null values are displayed
 - ``Null point mode`` - How null values are displayed
 - ``Staircase line`` - Draws adjacent points as staircase
 - ``Staircase line`` - Draws adjacent points as staircase
 
 
 ### Multiple Series
 ### Multiple Series
 
 
-If there are multiple series, they can be display as a group.
+If there are multiple series, they can be displayed as a group.
 
 
 - ``Stack`` - Each series is stacked on top of another
 - ``Stack`` - Each series is stacked on top of another
-- ``Percent`` - Each series is draw as a percent of the total of all series
+- ``Percent`` - Each series is drawn as a percentage of the total of all series
 
 
-If you have stack enabled you can select what the mouse hover feature should show.
+If you have stack enabled, you can select what the mouse hover feature should show.
 
 
 - Cumulative - Sum of series below plus the series you hover over
 - Cumulative - Sum of series below plus the series you hover over
 - Individual - Just the value for the series you hover over
 - Individual - Just the value for the series you hover over
@@ -134,11 +135,15 @@ If you have stack enabled you can select what the mouse hover feature should sho
 
 
 - ``All series`` - Show all series on the same tooltip and a x crosshairs to help follow all series
 - ``All series`` - Show all series on the same tooltip and a x crosshairs to help follow all series
 
 
-### Series specific overrides
+### Series Specific Overrides
+
+The section allows a series to be rendered differently from the others. For example, one series can be given
+a thicker line width to make it stand out.
+
+#### Dashes Drawing Style
 
 
-The section allows a series to be render different from the rest.  For example, one series can be given
-a thicker line width to make it standout.
+There is an option under Series overrides to draw lines as dashes. Set Dashes to the value True to override the line draw setting for a specific series.
 
 
-## Time range
+## Time Range
 
 
 ![](/img/docs/v2/graph_time_range.png)
 ![](/img/docs/v2/graph_time_range.png)

+ 1 - 0
docs/sources/features/panels/singlestat.md

@@ -2,6 +2,7 @@
 title = "Singlestat Panel"
 title = "Singlestat Panel"
 keywords = ["grafana", "dashboard", "documentation", "panels", "singlestat"]
 keywords = ["grafana", "dashboard", "documentation", "panels", "singlestat"]
 type = "docs"
 type = "docs"
+aliases = ["/reference/singlestat/"]
 [menu.docs]
 [menu.docs]
 name = "Singlestat"
 name = "Singlestat"
 parent = "panels"
 parent = "panels"

+ 1 - 0
docs/sources/features/panels/table_panel.md

@@ -2,6 +2,7 @@
 title = "Table Panel"
 title = "Table Panel"
 keywords = ["grafana", "dashboard", "documentation", "panels", "table panel"]
 keywords = ["grafana", "dashboard", "documentation", "panels", "table panel"]
 type = "docs"
 type = "docs"
+aliases = ["/reference/table/"]
 [menu.docs]
 [menu.docs]
 name = "Table"
 name = "Table"
 parent = "panels"
 parent = "panels"

+ 0 - 4
docs/sources/http_api/dashboard.md

@@ -221,10 +221,6 @@ Get all tags of dashboards
       }
       }
     ]
     ]
 
 
-## Dashboard from JSON file
-
-`GET /file/:file`
-
 ## Search Dashboards
 ## Search Dashboards
 
 
 `GET /api/search/`
 `GET /api/search/`

+ 3 - 1
docs/sources/installation/configuration.md

@@ -313,7 +313,6 @@ example:
     auth_url = https://github.com/login/oauth/authorize
     auth_url = https://github.com/login/oauth/authorize
     token_url = https://github.com/login/oauth/access_token
     token_url = https://github.com/login/oauth/access_token
     api_url = https://api.github.com/user
     api_url = https://api.github.com/user
-    allow_sign_up = false
     team_ids =
     team_ids =
     allowed_organizations =
     allowed_organizations =
 
 
@@ -644,6 +643,9 @@ Secret key. e.g. AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
 ### url
 ### url
 Url to where Grafana will send PUT request with images
 Url to where Grafana will send PUT request with images
 
 
+### public_url
+Optional parameter. Url to send to users in notifications, directly appended with the resulting uploaded file name.
+
 ### username
 ### username
 basic auth username
 basic auth username
 
 

+ 6 - 7
emails/templates/layouts/default.html

@@ -94,8 +94,7 @@ td[class="stack-column-center"] {
 	<table class="body" style="background: #2e2e2e;">
 	<table class="body" style="background: #2e2e2e;">
 		<tr>
 		<tr>
 			<td class="center" align="center" valign="top">
 			<td class="center" align="center" valign="top">
-        		<center>
-
+        <center>
 					<table class="row header">
 					<table class="row header">
 						<tr>
 						<tr>
 						  <td class="center" align="center">
 						  <td class="center" align="center">
@@ -107,11 +106,11 @@ td[class="stack-column-center"] {
 
 
 						            <table class="twelve columns">
 						            <table class="twelve columns">
 						              <tr>
 						              <tr>
-						                <td class="six sub-columns center">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; float: none; display: inline">
-						                </td>
-										<td class="expander"></td>
-						              </tr>
+						                <td class="twelve sub-columns center">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; float: none; display: inline">
+                            </td>
+                            <td class="expander"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>

+ 3 - 0
pkg/api/alerting.go

@@ -255,6 +255,9 @@ func NotificationTest(c *middleware.Context, dto dtos.NotificationTestCommand) R
 	}
 	}
 
 
 	if err := bus.Dispatch(cmd); err != nil {
 	if err := bus.Dispatch(cmd); err != nil {
+		if err == models.ErrSmtpNotEnabled {
+			return ApiError(412, err.Error(), err)
+		}
 		return ApiError(500, "Failed to send alert notifications", err)
 		return ApiError(500, "Failed to send alert notifications", err)
 	}
 	}
 
 

+ 1 - 1
pkg/api/datasources.go

@@ -20,7 +20,7 @@ func GetDataSources(c *middleware.Context) Response {
 
 
 	result := make(dtos.DataSourceList, 0)
 	result := make(dtos.DataSourceList, 0)
 	for _, ds := range query.Result {
 	for _, ds := range query.Result {
-		dsItem := dtos.DataSource{
+		dsItem := dtos.DataSourceListItemDTO{
 			Id:        ds.Id,
 			Id:        ds.Id,
 			OrgId:     ds.OrgId,
 			OrgId:     ds.OrgId,
 			Name:      ds.Name,
 			Name:      ds.Name,

+ 17 - 1
pkg/api/dtos/models.go

@@ -84,7 +84,23 @@ type DataSource struct {
 	SecureJsonFields  map[string]bool  `json:"secureJsonFields"`
 	SecureJsonFields  map[string]bool  `json:"secureJsonFields"`
 }
 }
 
 
-type DataSourceList []DataSource
+type DataSourceListItemDTO struct {
+	Id          int64            `json:"id"`
+	OrgId       int64            `json:"orgId"`
+	Name        string           `json:"name"`
+	Type        string           `json:"type"`
+	TypeLogoUrl string           `json:"typeLogoUrl"`
+	Access      m.DsAccess       `json:"access"`
+	Url         string           `json:"url"`
+	Password    string           `json:"password"`
+	User        string           `json:"user"`
+	Database    string           `json:"database"`
+	BasicAuth   bool             `json:"basicAuth"`
+	IsDefault   bool             `json:"isDefault"`
+	JsonData    *simplejson.Json `json:"jsonData,omitempty"`
+}
+
+type DataSourceList []DataSourceListItemDTO
 
 
 func (slice DataSourceList) Len() int {
 func (slice DataSourceList) Len() int {
 	return len(slice)
 	return len(slice)

+ 39 - 1
pkg/api/http_server.go

@@ -5,6 +5,7 @@ import (
 	"crypto/tls"
 	"crypto/tls"
 	"errors"
 	"errors"
 	"fmt"
 	"fmt"
+	"net"
 	"net/http"
 	"net/http"
 	"os"
 	"os"
 	"path"
 	"path"
@@ -13,9 +14,12 @@ import (
 
 
 	"github.com/grafana/grafana/pkg/api/live"
 	"github.com/grafana/grafana/pkg/api/live"
 	httpstatic "github.com/grafana/grafana/pkg/api/static"
 	httpstatic "github.com/grafana/grafana/pkg/api/static"
+	"github.com/grafana/grafana/pkg/bus"
 	"github.com/grafana/grafana/pkg/cmd/grafana-cli/logger"
 	"github.com/grafana/grafana/pkg/cmd/grafana-cli/logger"
+	"github.com/grafana/grafana/pkg/components/simplejson"
 	"github.com/grafana/grafana/pkg/log"
 	"github.com/grafana/grafana/pkg/log"
 	"github.com/grafana/grafana/pkg/middleware"
 	"github.com/grafana/grafana/pkg/middleware"
+	"github.com/grafana/grafana/pkg/models"
 	"github.com/grafana/grafana/pkg/plugins"
 	"github.com/grafana/grafana/pkg/plugins"
 	"github.com/grafana/grafana/pkg/setting"
 	"github.com/grafana/grafana/pkg/setting"
 )
 )
@@ -46,7 +50,7 @@ func (hs *HttpServer) Start(ctx context.Context) error {
 	hs.streamManager.Run(ctx)
 	hs.streamManager.Run(ctx)
 
 
 	listenAddr := fmt.Sprintf("%s:%s", setting.HttpAddr, setting.HttpPort)
 	listenAddr := fmt.Sprintf("%s:%s", setting.HttpAddr, setting.HttpPort)
-	hs.log.Info("Initializing HTTP Server", "address", listenAddr, "protocol", setting.Protocol, "subUrl", setting.AppSubUrl)
+	hs.log.Info("Initializing HTTP Server", "address", listenAddr, "protocol", setting.Protocol, "subUrl", setting.AppSubUrl, "socket", setting.SocketPath)
 
 
 	hs.httpSrv = &http.Server{Addr: listenAddr, Handler: hs.macaron}
 	hs.httpSrv = &http.Server{Addr: listenAddr, Handler: hs.macaron}
 	switch setting.Protocol {
 	switch setting.Protocol {
@@ -62,6 +66,18 @@ func (hs *HttpServer) Start(ctx context.Context) error {
 			hs.log.Debug("server was shutdown gracefully")
 			hs.log.Debug("server was shutdown gracefully")
 			return nil
 			return nil
 		}
 		}
+	case setting.SOCKET:
+		ln, err := net.Listen("unix", setting.SocketPath)
+		if err != nil {
+			hs.log.Debug("server was shutdown gracefully")
+			return nil
+		}
+
+		err = hs.httpSrv.Serve(ln)
+		if err != nil {
+			hs.log.Debug("server was shutdown gracefully")
+			return nil
+		}
 	default:
 	default:
 		hs.log.Error("Invalid protocol", "protocol", setting.Protocol)
 		hs.log.Error("Invalid protocol", "protocol", setting.Protocol)
 		err = errors.New("Invalid Protocol")
 		err = errors.New("Invalid Protocol")
@@ -147,6 +163,7 @@ func (hs *HttpServer) newMacaron() *macaron.Macaron {
 		Delims:     macaron.Delims{Left: "[[", Right: "]]"},
 		Delims:     macaron.Delims{Left: "[[", Right: "]]"},
 	}))
 	}))
 
 
+	m.Use(hs.healthHandler)
 	m.Use(middleware.GetContextHandler())
 	m.Use(middleware.GetContextHandler())
 	m.Use(middleware.Sessioner(&setting.SessionOptions))
 	m.Use(middleware.Sessioner(&setting.SessionOptions))
 	m.Use(middleware.RequestMetrics())
 	m.Use(middleware.RequestMetrics())
@@ -160,6 +177,27 @@ func (hs *HttpServer) newMacaron() *macaron.Macaron {
 	return m
 	return m
 }
 }
 
 
+func (hs *HttpServer) healthHandler(ctx *macaron.Context) {
+	if ctx.Req.Method != "GET" || ctx.Req.URL.Path != "/api/health" {
+		return
+	}
+
+	data := simplejson.New()
+	data.Set("database", "ok")
+	data.Set("version", setting.BuildVersion)
+	data.Set("commit", setting.BuildCommit)
+
+	if err := bus.Dispatch(&models.GetDBHealthQuery{}); err != nil {
+		data.Set("database", "failing")
+	}
+
+	ctx.Resp.Header().Set("Content-Type", "application/json; charset=UTF-8")
+	ctx.Resp.WriteHeader(200)
+
+	dataBytes, _ := data.EncodePretty()
+	ctx.Resp.Write(dataBytes)
+}
+
 func (hs *HttpServer) mapStatic(m *macaron.Macaron, rootDir string, dir string, prefix string) {
 func (hs *HttpServer) mapStatic(m *macaron.Macaron, rootDir string, dir string, prefix string) {
 	headers := func(c *macaron.Context) {
 	headers := func(c *macaron.Context) {
 		c.Resp.Header().Set("Cache-Control", "public, max-age=3600")
 		c.Resp.Header().Set("Cache-Control", "public, max-age=3600")

+ 2 - 4
pkg/api/login.go

@@ -11,7 +11,6 @@ import (
 	"github.com/grafana/grafana/pkg/middleware"
 	"github.com/grafana/grafana/pkg/middleware"
 	m "github.com/grafana/grafana/pkg/models"
 	m "github.com/grafana/grafana/pkg/models"
 	"github.com/grafana/grafana/pkg/setting"
 	"github.com/grafana/grafana/pkg/setting"
-	"github.com/grafana/grafana/pkg/util"
 )
 )
 
 
 const (
 const (
@@ -79,8 +78,7 @@ func tryLoginUsingRememberCookie(c *middleware.Context) bool {
 	user := userQuery.Result
 	user := userQuery.Result
 
 
 	// validate remember me cookie
 	// validate remember me cookie
-	if val, _ := c.GetSuperSecureCookie(
-		util.EncodeMd5(user.Rands+user.Password), setting.CookieRememberName); val != user.Login {
+	if val, _ := c.GetSuperSecureCookie(user.Rands+user.Password, setting.CookieRememberName); val != user.Login {
 		return false
 		return false
 	}
 	}
 
 
@@ -142,7 +140,7 @@ func loginUserWithUser(user *m.User, c *middleware.Context) {
 	days := 86400 * setting.LogInRememberDays
 	days := 86400 * setting.LogInRememberDays
 	if days > 0 {
 	if days > 0 {
 		c.SetCookie(setting.CookieUserName, user.Login, days, setting.AppSubUrl+"/")
 		c.SetCookie(setting.CookieUserName, user.Login, days, setting.AppSubUrl+"/")
-		c.SetSuperSecureCookie(util.EncodeMd5(user.Rands+user.Password), setting.CookieRememberName, user.Login, days, setting.AppSubUrl+"/")
+		c.SetSuperSecureCookie(user.Rands+user.Password, setting.CookieRememberName, user.Login, days, setting.AppSubUrl+"/")
 	}
 	}
 
 
 	c.Session.Set(middleware.SESS_KEY_USERID, user.Id)
 	c.Session.Set(middleware.SESS_KEY_USERID, user.Id)

+ 6 - 1
pkg/api/pluginproxy/pluginproxy_test.go

@@ -23,9 +23,14 @@ func TestPluginProxy(t *testing.T) {
 		setting.SecretKey = "password"
 		setting.SecretKey = "password"
 
 
 		bus.AddHandler("test", func(query *m.GetPluginSettingByIdQuery) error {
 		bus.AddHandler("test", func(query *m.GetPluginSettingByIdQuery) error {
+			key, err := util.Encrypt([]byte("123"), "password")
+			if err != nil {
+				return err
+			}
+
 			query.Result = &m.PluginSetting{
 			query.Result = &m.PluginSetting{
 				SecureJsonData: map[string][]byte{
 				SecureJsonData: map[string][]byte{
-					"key": util.Encrypt([]byte("123"), "password"),
+					"key": key,
 				},
 				},
 			}
 			}
 			return nil
 			return nil

+ 2 - 1
pkg/components/imguploader/imguploader.go

@@ -47,10 +47,11 @@ func NewImageUploader() (ImageUploader, error) {
 			return nil, fmt.Errorf("Could not find url key for image.uploader.webdav")
 			return nil, fmt.Errorf("Could not find url key for image.uploader.webdav")
 		}
 		}
 
 
+		public_url := webdavSec.Key("public_url").String()
 		username := webdavSec.Key("username").String()
 		username := webdavSec.Key("username").String()
 		password := webdavSec.Key("password").String()
 		password := webdavSec.Key("password").String()
 
 
-		return NewWebdavImageUploader(url, username, password)
+		return NewWebdavImageUploader(url, username, password, public_url)
 	}
 	}
 
 
 	return NopImageUploader{}, nil
 	return NopImageUploader{}, nil

+ 1 - 1
pkg/components/imguploader/s3uploader_test.go

@@ -8,7 +8,7 @@ import (
 )
 )
 
 
 func TestUploadToS3(t *testing.T) {
 func TestUploadToS3(t *testing.T) {
-	SkipConvey("[Integration test] for external_image_store.webdav", t, func() {
+	SkipConvey("[Integration test] for external_image_store.s3", t, func() {
 		setting.NewConfigContext(&setting.CommandLineArgs{
 		setting.NewConfigContext(&setting.CommandLineArgs{
 			HomePath: "../../../",
 			HomePath: "../../../",
 		})
 		})

+ 17 - 8
pkg/components/imguploader/webdavuploader.go

@@ -14,9 +14,10 @@ import (
 )
 )
 
 
 type WebdavUploader struct {
 type WebdavUploader struct {
-	url      string
-	username string
-	password string
+	url        string
+	username   string
+	password   string
+	public_url string
 }
 }
 
 
 var netTransport = &http.Transport{
 var netTransport = &http.Transport{
@@ -33,7 +34,8 @@ var netClient = &http.Client{
 
 
 func (u *WebdavUploader) Upload(pa string) (string, error) {
 func (u *WebdavUploader) Upload(pa string) (string, error) {
 	url, _ := url.Parse(u.url)
 	url, _ := url.Parse(u.url)
-	url.Path = path.Join(url.Path, util.GetRandomString(20)+".png")
+	filename := util.GetRandomString(20) + ".png"
+	url.Path = path.Join(url.Path, filename)
 
 
 	imgData, err := ioutil.ReadFile(pa)
 	imgData, err := ioutil.ReadFile(pa)
 	req, err := http.NewRequest("PUT", url.String(), bytes.NewReader(imgData))
 	req, err := http.NewRequest("PUT", url.String(), bytes.NewReader(imgData))
@@ -53,13 +55,20 @@ func (u *WebdavUploader) Upload(pa string) (string, error) {
 		return "", fmt.Errorf("Failed to upload image. Returned statuscode %v body %s", res.StatusCode, body)
 		return "", fmt.Errorf("Failed to upload image. Returned statuscode %v body %s", res.StatusCode, body)
 	}
 	}
 
 
+	if u.public_url != "" {
+		publicURL, _ := url.Parse(u.public_url)
+		publicURL.Path = path.Join(publicURL.Path, filename)
+		return publicURL.String(), nil
+	}
+
 	return url.String(), nil
 	return url.String(), nil
 }
 }
 
 
-func NewWebdavImageUploader(url, username, passwrod string) (*WebdavUploader, error) {
+func NewWebdavImageUploader(url, username, password, public_url string) (*WebdavUploader, error) {
 	return &WebdavUploader{
 	return &WebdavUploader{
-		url:      url,
-		username: username,
-		password: passwrod,
+		url:        url,
+		username:   username,
+		password:   password,
+		public_url: public_url,
 	}, nil
 	}, nil
 }
 }

+ 11 - 2
pkg/components/imguploader/webdavuploader_test.go

@@ -7,12 +7,21 @@ import (
 )
 )
 
 
 func TestUploadToWebdav(t *testing.T) {
 func TestUploadToWebdav(t *testing.T) {
-	webdavUploader, _ := NewWebdavImageUploader("http://localhost:9998/dav/", "username", "password")
 
 
+	// Can be tested with this docker container: https://hub.docker.com/r/morrisjobke/webdav/
 	SkipConvey("[Integration test] for external_image_store.webdav", t, func() {
 	SkipConvey("[Integration test] for external_image_store.webdav", t, func() {
+		webdavUploader, _ := NewWebdavImageUploader("http://localhost:8888/webdav/", "test", "test", "")
 		path, err := webdavUploader.Upload("../../../public/img/logo_transparent_400x.png")
 		path, err := webdavUploader.Upload("../../../public/img/logo_transparent_400x.png")
 
 
 		So(err, ShouldBeNil)
 		So(err, ShouldBeNil)
-		So(path, ShouldNotEqual, "")
+		So(path, ShouldStartWith, "http://localhost:8888/webdav/")
+	})
+
+	SkipConvey("[Integration test] for external_image_store.webdav with public url", t, func() {
+		webdavUploader, _ := NewWebdavImageUploader("http://localhost:8888/webdav/", "test", "test", "http://publicurl:8888/webdav")
+		path, err := webdavUploader.Upload("../../../public/img/logo_transparent_400x.png")
+
+		So(err, ShouldBeNil)
+		So(path, ShouldStartWith, "http://publicurl:8888/webdav/")
 	})
 	})
 }
 }

+ 13 - 2
pkg/components/securejsondata/securejsondata.go

@@ -1,6 +1,7 @@
 package securejsondata
 package securejsondata
 
 
 import (
 import (
+	"github.com/grafana/grafana/pkg/log"
 	"github.com/grafana/grafana/pkg/setting"
 	"github.com/grafana/grafana/pkg/setting"
 	"github.com/grafana/grafana/pkg/util"
 	"github.com/grafana/grafana/pkg/util"
 )
 )
@@ -10,7 +11,12 @@ type SecureJsonData map[string][]byte
 func (s SecureJsonData) Decrypt() map[string]string {
 func (s SecureJsonData) Decrypt() map[string]string {
 	decrypted := make(map[string]string)
 	decrypted := make(map[string]string)
 	for key, data := range s {
 	for key, data := range s {
-		decrypted[key] = string(util.Decrypt(data, setting.SecretKey))
+		decryptedData, err := util.Decrypt(data, setting.SecretKey)
+		if err != nil {
+			log.Fatal(4, err.Error())
+		}
+
+		decrypted[key] = string(decryptedData)
 	}
 	}
 	return decrypted
 	return decrypted
 }
 }
@@ -18,7 +24,12 @@ func (s SecureJsonData) Decrypt() map[string]string {
 func GetEncryptedJsonData(sjd map[string]string) SecureJsonData {
 func GetEncryptedJsonData(sjd map[string]string) SecureJsonData {
 	encrypted := make(SecureJsonData)
 	encrypted := make(SecureJsonData)
 	for key, data := range sjd {
 	for key, data := range sjd {
-		encrypted[key] = util.Encrypt([]byte(data), setting.SecretKey)
+		encryptedData, err := util.Encrypt([]byte(data), setting.SecretKey)
+		if err != nil {
+			log.Fatal(4, err.Error())
+		}
+
+		encrypted[key] = encryptedData
 	}
 	}
 	return encrypted
 	return encrypted
 }
 }

+ 4 - 2
pkg/log/log.go

@@ -15,6 +15,8 @@ import (
 	"github.com/go-stack/stack"
 	"github.com/go-stack/stack"
 	"github.com/inconshreveable/log15"
 	"github.com/inconshreveable/log15"
 	"github.com/inconshreveable/log15/term"
 	"github.com/inconshreveable/log15/term"
+
+	"github.com/grafana/grafana/pkg/util"
 )
 )
 
 
 var Root log15.Logger
 var Root log15.Logger
@@ -172,7 +174,7 @@ func ReadLoggingConfig(modes []string, logsPath string, cfg *ini.File) {
 	Close()
 	Close()
 
 
 	defaultLevelName, _ := getLogLevelFromConfig("log", "info", cfg)
 	defaultLevelName, _ := getLogLevelFromConfig("log", "info", cfg)
-	defaultFilters := getFilters(cfg.Section("log").Key("filters").Strings(" "))
+	defaultFilters := getFilters(util.SplitString(cfg.Section("log").Key("filters").String()))
 
 
 	handlers := make([]log15.Handler, 0)
 	handlers := make([]log15.Handler, 0)
 
 
@@ -185,7 +187,7 @@ func ReadLoggingConfig(modes []string, logsPath string, cfg *ini.File) {
 
 
 		// Log level.
 		// Log level.
 		_, level := getLogLevelFromConfig("log."+mode, defaultLevelName, cfg)
 		_, level := getLogLevelFromConfig("log."+mode, defaultLevelName, cfg)
-		modeFilters := getFilters(sec.Key("filters").Strings(" "))
+		modeFilters := getFilters(util.SplitString(sec.Key("filters").String()))
 		format := getLogFormat(sec.Key("format").MustString(""))
 		format := getLogFormat(sec.Key("format").MustString(""))
 
 
 		var handler log15.Handler
 		var handler log15.Handler

+ 8 - 3
pkg/models/datasource_cache_test.go

@@ -54,10 +54,15 @@ func TestDataSourceCache(t *testing.T) {
 		})
 		})
 
 
 		ds.JsonData = json
 		ds.JsonData = json
+
+		tlsCaCert, _ := util.Encrypt([]byte(caCert), "password")
+		tlsClientCert, _ := util.Encrypt([]byte(clientCert), "password")
+		tlsClientKey, _ := util.Encrypt([]byte(clientKey), "password")
+
 		ds.SecureJsonData = map[string][]byte{
 		ds.SecureJsonData = map[string][]byte{
-			"tlsCACert":     util.Encrypt([]byte(caCert), "password"),
-			"tlsClientCert": util.Encrypt([]byte(clientCert), "password"),
-			"tlsClientKey":  util.Encrypt([]byte(clientKey), "password"),
+			"tlsCACert":     tlsCaCert,
+			"tlsClientCert": tlsClientCert,
+			"tlsClientKey":  tlsClientKey,
 		}
 		}
 		ds.Updated = t.Add(-1 * time.Minute)
 		ds.Updated = t.Add(-1 * time.Minute)
 
 

+ 3 - 0
pkg/models/health.go

@@ -0,0 +1,3 @@
+package models
+
+type GetDBHealthQuery struct{}

+ 1 - 0
pkg/models/notifications.go

@@ -3,6 +3,7 @@ package models
 import "errors"
 import "errors"
 
 
 var ErrInvalidEmailCode = errors.New("Invalid or expired email code")
 var ErrInvalidEmailCode = errors.New("Invalid or expired email code")
+var ErrSmtpNotEnabled = errors.New("SMTP not configured, check your grafana.ini config file's [smtp] section.")
 
 
 type SendEmailCommand struct {
 type SendEmailCommand struct {
 	To           []string
 	To           []string

+ 1 - 1
pkg/services/notifications/mailer.go

@@ -107,7 +107,7 @@ func createDialer() (*gomail.Dialer, error) {
 
 
 func buildEmailMessage(cmd *m.SendEmailCommand) (*Message, error) {
 func buildEmailMessage(cmd *m.SendEmailCommand) (*Message, error) {
 	if !setting.Smtp.Enabled {
 	if !setting.Smtp.Enabled {
-		return nil, errors.New("Grafana mailing/smtp options not configured, contact your Grafana admin")
+		return nil, m.ErrSmtpNotEnabled
 	}
 	}
 
 
 	var buffer bytes.Buffer
 	var buffer bytes.Buffer

+ 14 - 0
pkg/services/sqlstore/health.go

@@ -0,0 +1,14 @@
+package sqlstore
+
+import (
+	"github.com/grafana/grafana/pkg/bus"
+	m "github.com/grafana/grafana/pkg/models"
+)
+
+func init() {
+	bus.AddHandler("sql", GetDBHealthQuery)
+}
+
+func GetDBHealthQuery(query *m.GetDBHealthQuery) error {
+	return x.Ping()
+}

+ 6 - 1
pkg/services/sqlstore/plugin_setting.go

@@ -74,7 +74,12 @@ func UpdatePluginSetting(cmd *m.UpdatePluginSettingCmd) error {
 			return err
 			return err
 		} else {
 		} else {
 			for key, data := range cmd.SecureJsonData {
 			for key, data := range cmd.SecureJsonData {
-				pluginSetting.SecureJsonData[key] = util.Encrypt([]byte(data), setting.SecretKey)
+				encryptedData, err := util.Encrypt([]byte(data), setting.SecretKey)
+				if err != nil {
+					return err
+				}
+
+				pluginSetting.SecureJsonData[key] = encryptedData
 			}
 			}
 
 
 			// add state change event on commit success
 			// add state change event on commit success

+ 1 - 0
pkg/services/sqlstore/sqlstore.go

@@ -158,6 +158,7 @@ func getEngine() (*xorm.Engine, error) {
 	} else {
 	} else {
 		engine.SetMaxOpenConns(DbCfg.MaxOpenConn)
 		engine.SetMaxOpenConns(DbCfg.MaxOpenConn)
 		engine.SetMaxIdleConns(DbCfg.MaxIdleConn)
 		engine.SetMaxIdleConns(DbCfg.MaxIdleConn)
+		engine.SetLogger(&xorm.DiscardLogger{})
 		// engine.SetLogger(NewXormLogger(log.LvlInfo, log.New("sqlstore.xorm")))
 		// engine.SetLogger(NewXormLogger(log.LvlInfo, log.New("sqlstore.xorm")))
 		// engine.ShowSQL = true
 		// engine.ShowSQL = true
 		// engine.ShowInfo = true
 		// engine.ShowInfo = true

+ 7 - 1
pkg/setting/setting.go

@@ -27,6 +27,7 @@ type Scheme string
 const (
 const (
 	HTTP              Scheme = "http"
 	HTTP              Scheme = "http"
 	HTTPS             Scheme = "https"
 	HTTPS             Scheme = "https"
+	SOCKET            Scheme = "socket"
 	DEFAULT_HTTP_ADDR string = "0.0.0.0"
 	DEFAULT_HTTP_ADDR string = "0.0.0.0"
 )
 )
 
 
@@ -65,6 +66,7 @@ var (
 	HttpAddr, HttpPort string
 	HttpAddr, HttpPort string
 	SshPort            int
 	SshPort            int
 	CertFile, KeyFile  string
 	CertFile, KeyFile  string
+	SocketPath         string
 	RouterLogging      bool
 	RouterLogging      bool
 	DataProxyLogging   bool
 	DataProxyLogging   bool
 	StaticRootPath     string
 	StaticRootPath     string
@@ -473,6 +475,10 @@ func NewConfigContext(args *CommandLineArgs) error {
 		CertFile = server.Key("cert_file").String()
 		CertFile = server.Key("cert_file").String()
 		KeyFile = server.Key("cert_key").String()
 		KeyFile = server.Key("cert_key").String()
 	}
 	}
+	if server.Key("protocol").MustString("http") == "socket" {
+		Protocol = SOCKET
+		SocketPath = server.Key("socket").String()
+	}
 
 
 	Domain = server.Key("domain").MustString("localhost")
 	Domain = server.Key("domain").MustString("localhost")
 	HttpAddr = server.Key("http_addr").MustString(DEFAULT_HTTP_ADDR)
 	HttpAddr = server.Key("http_addr").MustString(DEFAULT_HTTP_ADDR)
@@ -509,7 +515,7 @@ func NewConfigContext(args *CommandLineArgs) error {
 
 
 	//  read data source proxy white list
 	//  read data source proxy white list
 	DataProxyWhiteList = make(map[string]bool)
 	DataProxyWhiteList = make(map[string]bool)
-	for _, hostAndIp := range security.Key("data_source_proxy_whitelist").Strings(" ") {
+	for _, hostAndIp := range util.SplitString(security.Key("data_source_proxy_whitelist").String()) {
 		DataProxyWhiteList[hostAndIp] = true
 		DataProxyWhiteList[hostAndIp] = true
 	}
 	}
 
 

+ 6 - 5
pkg/social/social.go

@@ -8,6 +8,7 @@ import (
 	"golang.org/x/oauth2"
 	"golang.org/x/oauth2"
 
 
 	"github.com/grafana/grafana/pkg/setting"
 	"github.com/grafana/grafana/pkg/setting"
+	"github.com/grafana/grafana/pkg/util"
 )
 )
 
 
 type BasicUserInfo struct {
 type BasicUserInfo struct {
@@ -53,12 +54,12 @@ func NewOAuthService() {
 		info := &setting.OAuthInfo{
 		info := &setting.OAuthInfo{
 			ClientId:       sec.Key("client_id").String(),
 			ClientId:       sec.Key("client_id").String(),
 			ClientSecret:   sec.Key("client_secret").String(),
 			ClientSecret:   sec.Key("client_secret").String(),
-			Scopes:         sec.Key("scopes").Strings(" "),
+			Scopes:         util.SplitString(sec.Key("scopes").String()),
 			AuthUrl:        sec.Key("auth_url").String(),
 			AuthUrl:        sec.Key("auth_url").String(),
 			TokenUrl:       sec.Key("token_url").String(),
 			TokenUrl:       sec.Key("token_url").String(),
 			ApiUrl:         sec.Key("api_url").String(),
 			ApiUrl:         sec.Key("api_url").String(),
 			Enabled:        sec.Key("enabled").MustBool(),
 			Enabled:        sec.Key("enabled").MustBool(),
-			AllowedDomains: sec.Key("allowed_domains").Strings(" "),
+			AllowedDomains: util.SplitString(sec.Key("allowed_domains").String()),
 			HostedDomain:   sec.Key("hosted_domain").String(),
 			HostedDomain:   sec.Key("hosted_domain").String(),
 			AllowSignup:    sec.Key("allow_sign_up").MustBool(),
 			AllowSignup:    sec.Key("allow_sign_up").MustBool(),
 			Name:           sec.Key("name").MustString(name),
 			Name:           sec.Key("name").MustString(name),
@@ -92,7 +93,7 @@ func NewOAuthService() {
 				apiUrl:               info.ApiUrl,
 				apiUrl:               info.ApiUrl,
 				allowSignup:          info.AllowSignup,
 				allowSignup:          info.AllowSignup,
 				teamIds:              sec.Key("team_ids").Ints(","),
 				teamIds:              sec.Key("team_ids").Ints(","),
-				allowedOrganizations: sec.Key("allowed_organizations").Strings(" "),
+				allowedOrganizations: util.SplitString(sec.Key("allowed_organizations").String()),
 			}
 			}
 		}
 		}
 
 
@@ -115,7 +116,7 @@ func NewOAuthService() {
 				apiUrl:               info.ApiUrl,
 				apiUrl:               info.ApiUrl,
 				allowSignup:          info.AllowSignup,
 				allowSignup:          info.AllowSignup,
 				teamIds:              sec.Key("team_ids").Ints(","),
 				teamIds:              sec.Key("team_ids").Ints(","),
-				allowedOrganizations: sec.Key("allowed_organizations").Strings(" "),
+				allowedOrganizations: util.SplitString(sec.Key("allowed_organizations").String()),
 			}
 			}
 		}
 		}
 
 
@@ -135,7 +136,7 @@ func NewOAuthService() {
 				Config:               &config,
 				Config:               &config,
 				url:                  setting.GrafanaNetUrl,
 				url:                  setting.GrafanaNetUrl,
 				allowSignup:          info.AllowSignup,
 				allowSignup:          info.AllowSignup,
-				allowedOrganizations: sec.Key("allowed_organizations").Strings(" "),
+				allowedOrganizations: util.SplitString(sec.Key("allowed_organizations").String()),
 			}
 			}
 		}
 		}
 	}
 	}

+ 4 - 9
pkg/tsdb/influxdb/query.go

@@ -34,18 +34,13 @@ func (query *Query) Build(queryContext *tsdb.QueryContext) (string, error) {
 		return "", err
 		return "", err
 	}
 	}
 
 
-	res = replaceVariable(res, "$timeFilter", query.renderTimeFilter(queryContext))
-	res = replaceVariable(res, "$interval", interval.Text)
-	res = replaceVariable(res, "$__interval_ms", strconv.FormatInt(interval.Value.Nanoseconds()/int64(time.Millisecond), 10))
-	res = replaceVariable(res, "$__interval", interval.Text)
+	res = strings.Replace(res, "$timeFilter", query.renderTimeFilter(queryContext), -1)
+	res = strings.Replace(res, "$interval", interval.Text, -1)
+	res = strings.Replace(res, "$__interval_ms", strconv.FormatInt(interval.Value.Nanoseconds()/int64(time.Millisecond), 10), -1)
+	res = strings.Replace(res, "$__interval", interval.Text, -1)
 	return res, nil
 	return res, nil
 }
 }
 
 
-func replaceVariable(str string, variable string, value string) string {
-	count := strings.Count(str, variable)
-	return strings.Replace(str, variable, value, count)
-}
-
 func getDefinedInterval(query *Query, queryContext *tsdb.QueryContext) (*tsdb.Interval, error) {
 func getDefinedInterval(query *Query, queryContext *tsdb.QueryContext) (*tsdb.Interval, error) {
 	defaultInterval := tsdb.CalculateInterval(queryContext.TimeRange)
 	defaultInterval := tsdb.CalculateInterval(queryContext.TimeRange)
 
 

+ 9 - 10
pkg/util/encryption.go

@@ -5,26 +5,25 @@ import (
 	"crypto/cipher"
 	"crypto/cipher"
 	"crypto/rand"
 	"crypto/rand"
 	"crypto/sha256"
 	"crypto/sha256"
+	"errors"
 	"io"
 	"io"
-
-	"github.com/grafana/grafana/pkg/log"
 )
 )
 
 
 const saltLength = 8
 const saltLength = 8
 
 
-func Decrypt(payload []byte, secret string) []byte {
+func Decrypt(payload []byte, secret string) ([]byte, error) {
 	salt := payload[:saltLength]
 	salt := payload[:saltLength]
 	key := encryptionKeyToBytes(secret, string(salt))
 	key := encryptionKeyToBytes(secret, string(salt))
 
 
 	block, err := aes.NewCipher(key)
 	block, err := aes.NewCipher(key)
 	if err != nil {
 	if err != nil {
-		log.Fatal(4, err.Error())
+		return nil, err
 	}
 	}
 
 
 	// The IV needs to be unique, but not secure. Therefore it's common to
 	// The IV needs to be unique, but not secure. Therefore it's common to
 	// include it at the beginning of the ciphertext.
 	// include it at the beginning of the ciphertext.
 	if len(payload) < aes.BlockSize {
 	if len(payload) < aes.BlockSize {
-		log.Fatal(4, "payload too short")
+		return nil, errors.New("payload too short")
 	}
 	}
 	iv := payload[saltLength : saltLength+aes.BlockSize]
 	iv := payload[saltLength : saltLength+aes.BlockSize]
 	payload = payload[saltLength+aes.BlockSize:]
 	payload = payload[saltLength+aes.BlockSize:]
@@ -33,16 +32,16 @@ func Decrypt(payload []byte, secret string) []byte {
 
 
 	// XORKeyStream can work in-place if the two arguments are the same.
 	// XORKeyStream can work in-place if the two arguments are the same.
 	stream.XORKeyStream(payload, payload)
 	stream.XORKeyStream(payload, payload)
-	return payload
+	return payload, nil
 }
 }
 
 
-func Encrypt(payload []byte, secret string) []byte {
+func Encrypt(payload []byte, secret string) ([]byte, error) {
 	salt := GetRandomString(saltLength)
 	salt := GetRandomString(saltLength)
 
 
 	key := encryptionKeyToBytes(secret, salt)
 	key := encryptionKeyToBytes(secret, salt)
 	block, err := aes.NewCipher(key)
 	block, err := aes.NewCipher(key)
 	if err != nil {
 	if err != nil {
-		log.Fatal(4, err.Error())
+		return nil, err
 	}
 	}
 
 
 	// The IV needs to be unique, but not secure. Therefore it's common to
 	// The IV needs to be unique, but not secure. Therefore it's common to
@@ -51,13 +50,13 @@ func Encrypt(payload []byte, secret string) []byte {
 	copy(ciphertext[:saltLength], []byte(salt))
 	copy(ciphertext[:saltLength], []byte(salt))
 	iv := ciphertext[saltLength : saltLength+aes.BlockSize]
 	iv := ciphertext[saltLength : saltLength+aes.BlockSize]
 	if _, err := io.ReadFull(rand.Reader, iv); err != nil {
 	if _, err := io.ReadFull(rand.Reader, iv); err != nil {
-		log.Fatal(4, err.Error())
+		return nil, err
 	}
 	}
 
 
 	stream := cipher.NewCFBEncrypter(block, iv)
 	stream := cipher.NewCFBEncrypter(block, iv)
 	stream.XORKeyStream(ciphertext[saltLength+aes.BlockSize:], payload)
 	stream.XORKeyStream(ciphertext[saltLength+aes.BlockSize:], payload)
 
 
-	return ciphertext
+	return ciphertext, nil
 }
 }
 
 
 // Key needs to be 32bytes
 // Key needs to be 32bytes

+ 4 - 2
pkg/util/encryption_test.go

@@ -18,9 +18,11 @@ func TestEncryption(t *testing.T) {
 	})
 	})
 
 
 	Convey("When decrypting basic payload", t, func() {
 	Convey("When decrypting basic payload", t, func() {
-		encrypted := Encrypt([]byte("grafana"), "1234")
-		decrypted := Decrypt(encrypted, "1234")
+		encrypted, encryptErr := Encrypt([]byte("grafana"), "1234")
+		decrypted, decryptErr := Decrypt(encrypted, "1234")
 
 
+		So(encryptErr, ShouldBeNil)
+		So(decryptErr, ShouldBeNil)
 		So(string(decrypted), ShouldEqual, "grafana")
 		So(string(decrypted), ShouldEqual, "grafana")
 	})
 	})
 
 

+ 12 - 0
pkg/util/strings.go

@@ -1,5 +1,9 @@
 package util
 package util
 
 
+import (
+	"regexp"
+)
+
 func StringsFallback2(val1 string, val2 string) string {
 func StringsFallback2(val1 string, val2 string) string {
 	return stringsFallback(val1, val2)
 	return stringsFallback(val1, val2)
 }
 }
@@ -16,3 +20,11 @@ func stringsFallback(vals ...string) string {
 	}
 	}
 	return ""
 	return ""
 }
 }
+
+func SplitString(str string) []string {
+	if len(str) == 0 {
+		return []string{}
+	}
+
+	return regexp.MustCompile("[, ]+").Split(str, -1)
+}

+ 11 - 0
pkg/util/strings_test.go

@@ -13,3 +13,14 @@ func TestStringsUtil(t *testing.T) {
 		So(StringsFallback3("", "", "3"), ShouldEqual, "3")
 		So(StringsFallback3("", "", "3"), ShouldEqual, "3")
 	})
 	})
 }
 }
+
+func TestSplitString(t *testing.T) {
+	Convey("Splits strings correctly", t, func() {
+		So(SplitString(""), ShouldResemble, []string{})
+		So(SplitString("test"), ShouldResemble, []string{"test"})
+		So(SplitString("test1 test2 test3"), ShouldResemble, []string{"test1", "test2", "test3"})
+		So(SplitString("test1,test2,test3"), ShouldResemble, []string{"test1", "test2", "test3"})
+		So(SplitString("test1, test2, test3"), ShouldResemble, []string{"test1", "test2", "test3"})
+		So(SplitString("test1 , test2 test3"), ShouldResemble, []string{"test1", "test2", "test3"})
+	})
+}

+ 12 - 1
public/app/core/time_series2.ts

@@ -35,6 +35,7 @@ export default class TimeSeries {
   isOutsideRange: boolean;
   isOutsideRange: boolean;
 
 
   lines: any;
   lines: any;
+  dashes: any;
   bars: any;
   bars: any;
   points: any;
   points: any;
   yaxis: any;
   yaxis: any;
@@ -61,6 +62,9 @@ export default class TimeSeries {
 
 
   applySeriesOverrides(overrides) {
   applySeriesOverrides(overrides) {
     this.lines = {};
     this.lines = {};
+    this.dashes = {
+      dashLength: []
+    };
     this.points = {};
     this.points = {};
     this.bars = {};
     this.bars = {};
     this.yaxis = 1;
     this.yaxis = 1;
@@ -74,11 +78,18 @@ export default class TimeSeries {
         continue;
         continue;
       }
       }
       if (override.lines !== void 0) { this.lines.show = override.lines; }
       if (override.lines !== void 0) { this.lines.show = override.lines; }
+      if (override.dashes !== void 0) {
+         this.dashes.show = override.dashes;
+         this.lines.lineWidth = 0;
+      }
       if (override.points !== void 0) { this.points.show = override.points; }
       if (override.points !== void 0) { this.points.show = override.points; }
       if (override.bars !== void 0) { this.bars.show = override.bars; }
       if (override.bars !== void 0) { this.bars.show = override.bars; }
       if (override.fill !== void 0) { this.lines.fill = translateFillOption(override.fill); }
       if (override.fill !== void 0) { this.lines.fill = translateFillOption(override.fill); }
       if (override.stack !== void 0) { this.stack = override.stack; }
       if (override.stack !== void 0) { this.stack = override.stack; }
-      if (override.linewidth !== void 0) { this.lines.lineWidth = override.linewidth; }
+      if (override.linewidth !== void 0) {
+         this.lines.lineWidth = override.linewidth;
+         this.dashes.lineWidth = override.linewidth;
+      }
       if (override.nullPointMode !== void 0) { this.nullPointMode = override.nullPointMode; }
       if (override.nullPointMode !== void 0) { this.nullPointMode = override.nullPointMode; }
       if (override.pointradius !== void 0) { this.points.radius = override.pointradius; }
       if (override.pointradius !== void 0) { this.points.radius = override.pointradius; }
       if (override.steppedLine !== void 0) { this.lines.steps = override.steppedLine; }
       if (override.steppedLine !== void 0) { this.lines.steps = override.steppedLine; }

+ 7 - 0
public/app/features/annotations/annotations_srv.ts

@@ -144,6 +144,13 @@ export class AnnotationsSrv {
   }
   }
 
 
   translateQueryResult(annotation, results) {
   translateQueryResult(annotation, results) {
+    // if annotation has snapshotData
+    // make clone and remove it
+    if (annotation.snapshotData) {
+      annotation = angular.copy(annotation);
+      delete annotation.snapshotData;
+    }
+
     for (var item of results) {
     for (var item of results) {
       item.source = annotation;
       item.source = annotation;
       item.min = item.time;
       item.min = item.time;

+ 1 - 1
public/app/features/annotations/event_manager.ts

@@ -58,7 +58,7 @@ export class EventManager {
   }
   }
 
 
   addFlotEvents(annotations, flotOptions) {
   addFlotEvents(annotations, flotOptions) {
-    if (!this.event || annotations.length === 0) {
+    if (!this.event && annotations.length === 0) {
       return;
       return;
     }
     }
 
 

+ 3 - 3
public/app/features/annotations/partials/editor.html

@@ -65,7 +65,7 @@
 				<h5 class="section-heading">Options</h5>
 				<h5 class="section-heading">Options</h5>
 					<div class="gf-form-inline">
 					<div class="gf-form-inline">
 						<div class="gf-form">
 						<div class="gf-form">
-							<span class="gf-form-label width-7">Name</span>
+							<span class="gf-form-label width-9">Name</span>
 							<input type="text" class="gf-form-input width-12" ng-model='ctrl.currentAnnotation.name' placeholder="name"></input>
 							<input type="text" class="gf-form-input width-12" ng-model='ctrl.currentAnnotation.name' placeholder="name"></input>
 						</div>
 						</div>
 						<div class="gf-form">
 						<div class="gf-form">
@@ -87,11 +87,11 @@
 															label="Hide toggle"
 															label="Hide toggle"
 															tooltip="Hides the annotation query toggle from showing at the top of the dashboard"
 															tooltip="Hides the annotation query toggle from showing at the top of the dashboard"
 															checked="ctrl.currentAnnotation.hide"
 															checked="ctrl.currentAnnotation.hide"
-															label-class="width-7">
+															label-class="width-9">
 							</gf-form-switch>
 							</gf-form-switch>
 						</div>
 						</div>
 						<div class="gf-form">
 						<div class="gf-form">
-							<label class="gf-form-label width-7">Color</label>
+							<label class="gf-form-label width-9">Color</label>
 							<spectrum-picker class="gf-form-input width-3" ng-model="ctrl.currentAnnotation.iconColor"></spectrum-picker>
 							<spectrum-picker class="gf-form-input width-3" ng-model="ctrl.currentAnnotation.iconColor"></spectrum-picker>
 						</div>
 						</div>
 					</div>
 					</div>

+ 1 - 0
public/app/features/dashboard/shareSnapshotCtrl.js

@@ -116,6 +116,7 @@ function (angular, _) {
         return {
         return {
           name: annotation.name,
           name: annotation.name,
           enable: annotation.enable,
           enable: annotation.enable,
+          iconColor: annotation.iconColor,
           snapshotData: annotation.snapshotData
           snapshotData: annotation.snapshotData
         };
         };
       }).value();
       }).value();

+ 1 - 1
public/app/plugins/datasource/influxdb/influx_query.ts

@@ -194,7 +194,7 @@ export default class InfluxQuery {
     }
     }
 
 
     var escapedValues = _.map(value, kbn.regexEscape);
     var escapedValues = _.map(value, kbn.regexEscape);
-    return escapedValues.join('|');
+    return '(' + escapedValues.join('|') + ')';
   }
   }
 
 
   render(interpolate?) {
   render(interpolate?) {

+ 53 - 13
public/app/plugins/datasource/prometheus/datasource.ts

@@ -7,6 +7,7 @@ import moment from 'moment';
 import kbn from 'app/core/utils/kbn';
 import kbn from 'app/core/utils/kbn';
 import * as dateMath from 'app/core/utils/datemath';
 import * as dateMath from 'app/core/utils/datemath';
 import PrometheusMetricFindQuery from './metric_find_query';
 import PrometheusMetricFindQuery from './metric_find_query';
+import TableModel from 'app/core/table_model';
 
 
 var durationSplitRegexp = /(\d+)(ms|s|m|h|d|w|M|y)/;
 var durationSplitRegexp = /(\d+)(ms|s|m|h|d|w|M|y)/;
 
 
@@ -20,7 +21,6 @@ export function PrometheusDatasource(instanceSettings, $q, backendSrv, templateS
   this.directUrl = instanceSettings.directUrl;
   this.directUrl = instanceSettings.directUrl;
   this.basicAuth = instanceSettings.basicAuth;
   this.basicAuth = instanceSettings.basicAuth;
   this.withCredentials = instanceSettings.withCredentials;
   this.withCredentials = instanceSettings.withCredentials;
-  this.lastErrors = {};
 
 
   this._request = function(method, url, requestId) {
   this._request = function(method, url, requestId) {
     var options: any = {
     var options: any = {
@@ -74,7 +74,7 @@ export function PrometheusDatasource(instanceSettings, $q, backendSrv, templateS
 
 
     options = _.clone(options);
     options = _.clone(options);
 
 
-    _.each(options.targets, target => {
+    for (let target of options.targets) {
       if (!target.expr || target.hide) {
       if (!target.expr || target.hide) {
         return;
         return;
       }
       }
@@ -91,31 +91,33 @@ export function PrometheusDatasource(instanceSettings, $q, backendSrv, templateS
       var range = Math.ceil(end - start);
       var range = Math.ceil(end - start);
       target.step = query.step = this.adjustStep(query.step, this.intervalSeconds(options.interval), range);
       target.step = query.step = this.adjustStep(query.step, this.intervalSeconds(options.interval), range);
       queries.push(query);
       queries.push(query);
-    });
+    }
 
 
     // No valid targets, return the empty result to save a round trip.
     // No valid targets, return the empty result to save a round trip.
     if (_.isEmpty(queries)) {
     if (_.isEmpty(queries)) {
-      var d = $q.defer();
-      d.resolve({ data: [] });
-      return d.promise;
+      return $q.when({ data: [] });
     }
     }
 
 
     var allQueryPromise = _.map(queries, query => {
     var allQueryPromise = _.map(queries, query => {
       return this.performTimeSeriesQuery(query, start, end);
       return this.performTimeSeriesQuery(query, start, end);
     });
     });
 
 
-    return $q.all(allQueryPromise).then(function(allResponse) {
+    return $q.all(allQueryPromise).then(responseList => {
       var result = [];
       var result = [];
+      var index = 0;
 
 
-      _.each(allResponse, function(response, index) {
+      _.each(responseList, (response, index) => {
         if (response.status === 'error') {
         if (response.status === 'error') {
-          self.lastErrors.query = response.error;
           throw response.error;
           throw response.error;
         }
         }
-        delete self.lastErrors.query;
-        _.each(response.data.data.result, function(metricData) {
-          result.push(self.transformMetricData(metricData, activeTargets[index], start, end));
-        });
+
+        if (activeTargets[index].format === "table") {
+          result.push(self.transformMetricDataToTable(response.data.data.result));
+        } else {
+          for (let metricData of response.data.data.result) {
+            result.push(self.transformMetricData(metricData, activeTargets[index], start, end));
+          }
+        }
       });
       });
 
 
       return { data: result };
       return { data: result };
@@ -273,6 +275,44 @@ export function PrometheusDatasource(instanceSettings, $q, backendSrv, templateS
     return { target: metricLabel, datapoints: dps };
     return { target: metricLabel, datapoints: dps };
   };
   };
 
 
+  this.transformMetricDataToTable = function(series) {
+    var table = new TableModel();
+    var self = this;
+    var i, j;
+
+    if (series.length === 0) {
+      return table;
+    }
+
+    _.each(series, function(series, seriesIndex) {
+      if (seriesIndex === 0) {
+        table.columns.push({text: 'Time', type: 'time'});
+        _.each(_.keys(series.metric), function(key) {
+          table.columns.push({text: key});
+        });
+        table.columns.push({text: 'Value'});
+      }
+
+      if (series.values) {
+        for (i = 0; i < series.values.length; i++) {
+          var values = series.values[i];
+          var reordered = [values[0] * 1000];
+          if (series.metric) {
+            for (var key in series.metric) {
+              if (series.metric.hasOwnProperty(key)) {
+                reordered.push(series.metric[key]);
+              }
+            }
+          }
+          reordered.push(parseFloat(values[1]));
+          table.rows.push(reordered);
+        }
+      }
+    });
+
+    return table;
+  };
+
   this.createMetricLabel = function(labelData, options) {
   this.createMetricLabel = function(labelData, options) {
     if (_.isUndefined(options) || _.isEmpty(options.legendFormat)) {
     if (_.isUndefined(options) || _.isEmpty(options.legendFormat)) {
       return this.getOriginalMetricName(labelData);
       return this.getOriginalMetricName(labelData);

+ 4 - 0
public/app/plugins/datasource/prometheus/partials/query.editor.html

@@ -42,6 +42,10 @@
 		</div>
 		</div>
 
 
 		<div class="gf-form">
 		<div class="gf-form">
+			<label class="gf-form-label">Format as</label>
+			<div class="gf-form-select-wrapper">
+				<select class="gf-form-input gf-size-auto" ng-model="ctrl.target.format" ng-options="f.value as f.text for f in ctrl.formats" ng-change="ctrl.refresh()"></select>
+			</div>
 			<label class="gf-form-label">
 			<label class="gf-form-label">
 				<a href="{{ctrl.linkToPrometheus}}" target="_blank" bs-tooltip="'Link to Graph in Prometheus'">
 				<a href="{{ctrl.linkToPrometheus}}" target="_blank" bs-tooltip="'Link to Graph in Prometheus'">
 					<i class="fa fa-share-square-o"></i>
 					<i class="fa fa-share-square-o"></i>

+ 14 - 1
public/app/plugins/datasource/prometheus/query_ctrl.ts

@@ -12,6 +12,7 @@ class PrometheusQueryCtrl extends QueryCtrl {
 
 
   metric: any;
   metric: any;
   resolutions: any;
   resolutions: any;
+  formats: any;
   oldTarget: any;
   oldTarget: any;
   suggestMetrics: any;
   suggestMetrics: any;
   linkToPrometheus: any;
   linkToPrometheus: any;
@@ -23,15 +24,20 @@ class PrometheusQueryCtrl extends QueryCtrl {
     var target = this.target;
     var target = this.target;
     target.expr = target.expr || '';
     target.expr = target.expr || '';
     target.intervalFactor = target.intervalFactor || 2;
     target.intervalFactor = target.intervalFactor || 2;
+    target.format = target.format || this.getDefaultFormat();
 
 
     this.metric = '';
     this.metric = '';
     this.resolutions = _.map([1,2,3,4,5,10], function(f) {
     this.resolutions = _.map([1,2,3,4,5,10], function(f) {
       return {factor: f, label: '1/' + f};
       return {factor: f, label: '1/' + f};
     });
     });
 
 
+    this.formats = [
+      {text: 'Time series', value: 'time_series'},
+      {text: 'Table', value: 'table'},
+    ];
+
     $scope.$on('typeahead-updated', () => {
     $scope.$on('typeahead-updated', () => {
       this.$scope.$apply(() => {
       this.$scope.$apply(() => {
-
         this.target.expr += this.target.metric;
         this.target.expr += this.target.metric;
         this.metric = '';
         this.metric = '';
         this.refreshMetricData();
         this.refreshMetricData();
@@ -48,6 +54,13 @@ class PrometheusQueryCtrl extends QueryCtrl {
     this.updateLink();
     this.updateLink();
   }
   }
 
 
+  getDefaultFormat() {
+    if (this.panelCtrl.panel.type === 'table') {
+      return 'table';
+    }
+    return 'time_series';
+  }
+
   refreshMetricData() {
   refreshMetricData() {
     if (!_.isEqual(this.oldTarget, this.target)) {
     if (!_.isEqual(this.oldTarget, this.target)) {
       this.oldTarget = angular.copy(this.target);
       this.oldTarget = angular.copy(this.target);

+ 24 - 0
public/app/plugins/datasource/prometheus/specs/datasource_specs.ts

@@ -160,4 +160,28 @@ describe('PrometheusDatasource', function() {
       expect(results[0].time).to.be(1443454528 * 1000);
       expect(results[0].time).to.be(1443454528 * 1000);
     });
     });
   });
   });
+  describe('When resultFormat is table', function() {
+    var response = {
+      status: "success",
+      data: {
+        resultType: "matrix",
+        result: [{
+          metric: {"__name__": "test", job: "testjob"},
+          values: [[1443454528, "3846"]]
+        }]
+      }
+    };
+    it('should return table model', function() {
+      var table = ctx.ds.transformMetricDataToTable(response.data.result);
+      expect(table.type).to.be('table');
+      expect(table.rows).to.eql([ [ 1443454528000, 'test', 'testjob', 3846 ] ]);
+      expect(table.columns).to.eql(
+        [ { text: 'Time', type: 'time' },
+          { text: '__name__' },
+          { text: 'job' },
+          { text: 'Value' }
+        ]
+      );
+    });
+  });
 });
 });

+ 10 - 1
public/app/plugins/panel/graph/graph.ts

@@ -7,6 +7,7 @@ import 'jquery.flot.stack';
 import 'jquery.flot.stackpercent';
 import 'jquery.flot.stackpercent';
 import 'jquery.flot.fillbelow';
 import 'jquery.flot.fillbelow';
 import 'jquery.flot.crosshair';
 import 'jquery.flot.crosshair';
+import 'jquery.flot.dashes';
 import './jquery.flot.events';
 import './jquery.flot.events';
 
 
 import $ from 'jquery';
 import $ from 'jquery';
@@ -215,6 +216,9 @@ coreModule.directive('grafanaGraph', function($rootScope, timeSrv, popoverSrv) {
         // give space to alert editing
         // give space to alert editing
         thresholdManager.prepare(elem, data);
         thresholdManager.prepare(elem, data);
 
 
+        // un-check dashes if lines are unchecked
+        panel.dashes = panel.lines ? panel.dashes : false;
+
         var stack = panel.stack ? true : null;
         var stack = panel.stack ? true : null;
 
 
         // Populate element
         // Populate element
@@ -231,9 +235,14 @@ coreModule.directive('grafanaGraph', function($rootScope, timeSrv, popoverSrv) {
               show: panel.lines,
               show: panel.lines,
               zero: false,
               zero: false,
               fill: translateFillOption(panel.fill),
               fill: translateFillOption(panel.fill),
-              lineWidth: panel.linewidth,
+              lineWidth: panel.dashes ? 0 : panel.linewidth,
               steps: panel.steppedLine
               steps: panel.steppedLine
             },
             },
+            dashes: {
+              show: panel.dashes,
+              lineWidth: panel.linewidth,
+              dashLength: [panel.dashLength, panel.spaceLength]
+            },
             bars: {
             bars: {
               show: panel.bars,
               show: panel.bars,
               fill: 1,
               fill: 1,

+ 6 - 0
public/app/plugins/panel/graph/module.ts

@@ -67,6 +67,12 @@ class GraphCtrl extends MetricsPanelCtrl {
     fill          : 1,
     fill          : 1,
     // line width in pixels
     // line width in pixels
     linewidth     : 1,
     linewidth     : 1,
+    // show/hide dashed line
+    dashes        : false,
+    // length of a dash
+    dashLength    : 10,
+    // length of space between two dashes
+    spaceLength   : 10,
     // show hide points
     // show hide points
     points        : false,
     points        : false,
     // point radius in pixels
     // point radius in pixels

+ 1 - 0
public/app/plugins/panel/graph/series_overrides_ctrl.js

@@ -100,6 +100,7 @@ define([
     $scope.addOverrideOption('Null point mode', 'nullPointMode', ['connected', 'null', 'null as zero']);
     $scope.addOverrideOption('Null point mode', 'nullPointMode', ['connected', 'null', 'null as zero']);
     $scope.addOverrideOption('Fill below to', 'fillBelowTo', $scope.getSeriesNames());
     $scope.addOverrideOption('Fill below to', 'fillBelowTo', $scope.getSeriesNames());
     $scope.addOverrideOption('Staircase line', 'steppedLine', [true, false]);
     $scope.addOverrideOption('Staircase line', 'steppedLine', [true, false]);
+    $scope.addOverrideOption('Dashes', 'dashes', [true, false]);
     $scope.addOverrideOption('Points', 'points', [true, false]);
     $scope.addOverrideOption('Points', 'points', [true, false]);
     $scope.addOverrideOption('Points Radius', 'pointradius', [1,2,3,4,5]);
     $scope.addOverrideOption('Points Radius', 'pointradius', [1,2,3,4,5]);
     $scope.addOverrideOption('Stack', 'stack', [true, false, 'A', 'B', 'C', 'D']);
     $scope.addOverrideOption('Stack', 'stack', [true, false, 'A', 'B', 'C', 'D']);

+ 14 - 0
public/app/plugins/panel/graph/specs/graph_specs.ts

@@ -153,6 +153,20 @@ describe('grafanaGraph', function() {
     });
     });
   });
   });
 
 
+  graphScenario('dashed lines options', function(ctx) {
+    ctx.setup(function(ctrl) {
+      ctrl.panel.lines = true;
+      ctrl.panel.linewidth = 2;
+      ctrl.panel.dashes = true;
+    });
+
+    it('should configure dashed plot with correct options', function() {
+      expect(ctx.plotOptions.series.lines.show).to.be(true);
+      expect(ctx.plotOptions.series.dashes.lineWidth).to.be(2);
+      expect(ctx.plotOptions.series.dashes.show).to.be(true);
+    });
+  });
+
   graphScenario('should use timeStep for barWidth', function(ctx) {
   graphScenario('should use timeStep for barWidth', function(ctx) {
     ctx.setup(function(ctrl, data) {
     ctx.setup(function(ctrl, data) {
       ctrl.panel.bars = true;
       ctrl.panel.bars = true;

+ 1 - 1
public/app/plugins/panel/graph/tab_display.html

@@ -32,7 +32,7 @@
 					<select class="gf-form-input" ng-model="ctrl.panel.fill" ng-options="f for f in [0,1,2,3,4,5,6,7,8,9,10]" ng-change="ctrl.render()"></select>
 					<select class="gf-form-input" ng-model="ctrl.panel.fill" ng-options="f for f in [0,1,2,3,4,5,6,7,8,9,10]" ng-change="ctrl.render()"></select>
 				</div>
 				</div>
 			</div>
 			</div>
-			<div class="gf-form" ng-show="ctrl.panel.lines">
+			<div class="gf-form" ng-show="(ctrl.panel.lines)">
 				<label class="gf-form-label width-8">Line Width</label>
 				<label class="gf-form-label width-8">Line Width</label>
 				<div class="gf-form-select-wrapper max-width-5">
 				<div class="gf-form-select-wrapper max-width-5">
 					<select class="gf-form-input" ng-model="ctrl.panel.linewidth" ng-options="f for f in [0,1,2,3,4,5,6,7,8,9,10]" ng-change="ctrl.render()"></select>
 					<select class="gf-form-input" ng-model="ctrl.panel.linewidth" ng-options="f for f in [0,1,2,3,4,5,6,7,8,9,10]" ng-change="ctrl.render()"></select>

+ 2 - 2
public/app/plugins/panel/heatmap/axes_editor.ts

@@ -26,8 +26,8 @@ export class AxesEditorCtrl {
     };
     };
 
 
     this.dataFormats = {
     this.dataFormats = {
-      'TS': 'timeseries',
-      'TS Pre-bucketed': 'tsbuckets'
+      'Time series': 'timeseries',
+      'Time series Pre-bucketed': 'tsbuckets'
     };
     };
   }
   }
 
 

+ 2 - 1
public/app/system.conf.js

@@ -31,7 +31,8 @@ System.config({
     "jquery.flot.crosshair": "vendor/flot/jquery.flot.crosshair",
     "jquery.flot.crosshair": "vendor/flot/jquery.flot.crosshair",
     "jquery.flot.fillbelow": "vendor/flot/jquery.flot.fillbelow",
     "jquery.flot.fillbelow": "vendor/flot/jquery.flot.fillbelow",
     "jquery.flot.gauge": "vendor/flot/jquery.flot.gauge",
     "jquery.flot.gauge": "vendor/flot/jquery.flot.gauge",
-    "d3": "vendor/d3/d3.js"
+    "d3": "vendor/d3/d3.js",
+    "jquery.flot.dashes": "vendor/flot/jquery.flot.dashes"
   },
   },
 
 
   packages: {
   packages: {

+ 3 - 0
public/dashboards/default.json

@@ -82,6 +82,9 @@
           "lines": true,
           "lines": true,
           "fill": 1,
           "fill": 1,
           "linewidth": 2,
           "linewidth": 2,
+          "dashes": false,
+          "dashLength": 10,
+          "spaceLength": 10,
           "points": false,
           "points": false,
           "pointradius": 5,
           "pointradius": 5,
           "bars": false,
           "bars": false,

+ 3 - 0
public/dashboards/template_vars.json

@@ -50,6 +50,9 @@
           "lines": true,
           "lines": true,
           "fill": 1,
           "fill": 1,
           "linewidth": 1,
           "linewidth": 1,
+          "dashes": false,
+          "dashLength": 10,
+          "spaceLength": 10,
           "points": false,
           "points": false,
           "pointradius": 5,
           "pointradius": 5,
           "bars": false,
           "bars": false,

+ 87 - 89
public/emails/alert_notification.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,21 +198,21 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								{{Subject .Subject "{{.Title}}"}}
 								{{Subject .Subject "{{.Title}}"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-  <tr style="padding: 0; vertical-align: top;" align="left">
-    <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-      <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-            <h3 style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; /*text-align: center*/; color: {{.SeverityColor}}; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 22px; font-style: italic; font-weight: bold; line-height: 1.3; margin: 10px 0; padding: 0; word-break: normal;" align="left">{{.Title}}</h3>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+  <tr style="vertical-align: top; padding: 0;" align="left">
+    <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+      <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+            <h3 style="/*text-align: center*/; color: {{.SeverityColor}}; font-weight: bold; font-style: italic; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; line-height: 1.3; word-break: normal; font-size: 22px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 10px 0; padding: 0;" align="left">{{.Title}}</h3>
           </td>
           </td>
         </tr>
         </tr>
       </table>
       </table>
@@ -222,13 +220,13 @@ text-decoration: underline;
   </tr>
   </tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-  <tr style="padding: 0; vertical-align: top;" align="left">
-    <td class="last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0 0px 0 0; word-break: break-word;" align="left" valign="top">
-      <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-            <p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; /*text-align: center*/; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">{{.Message}}</p>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+  <tr style="vertical-align: top; padding: 0;" align="left">
+    <td class="last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0 0px 0 0;" align="left" valign="top">
+      <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+            <p style="/*text-align: center*/; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">{{.Message}}</p>
           </td>
           </td>
         </tr>
         </tr>
       </table>
       </table>
@@ -237,26 +235,26 @@ text-decoration: underline;
 </table>
 </table>
 
 
 {{if ne .State "ok" }}
 {{if ne .State "ok" }}
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-  <tr style="padding: 0; vertical-align: top;" align="left">
-    <td class="last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0 0px 0 0; word-break: break-word;" align="left" valign="top">
-      <center style="min-width: 580px; width: 100%;">
-      <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="six" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 50%; word-break: break-word;" align="left" valign="top">
-            <h5 style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 18px; font-weight: bold; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="left">Metric name</h5>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+  <tr style="vertical-align: top; padding: 0;" align="left">
+    <td class="last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0 0px 0 0;" align="left" valign="top">
+      <center style="width: 100%; min-width: 580px;">
+      <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="six" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 50%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+            <h5 style="font-weight: bold; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; line-height: 1.3; word-break: normal; font-size: 18px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left">Metric name</h5>
           </td>
           </td>
-          <td class="six last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100px; word-break: break-word;" align="right" valign="top">
-            <h5 style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 18px; font-weight: bold; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="right">Value</h5>
+          <td class="six last" style="width: 100px; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="right" valign="top">
+            <h5 style="font-weight: bold; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; line-height: 1.3; word-break: normal; font-size: 18px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="right">Value</h5>
           </td>
           </td>
         </tr>
         </tr>
         {{range .EvalMatches}}
         {{range .EvalMatches}}
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="six" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 50%; word-break: break-word;" align="left" valign="top">
-            <h5 class="data" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 16px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="left">{{.Metric}}</h5>
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="six" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 50%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+            <h5 class="data" style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 16px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left">{{.Metric}}</h5>
           </td>
           </td>
-          <td class="six last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100px; word-break: break-word;" align="right" valign="top">
-            <h5 class="data" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 16px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="right">{{.Value}}</h5>
+          <td class="six last" style="width: 100px; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="right" valign="top">
+            <h5 class="data" style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 16px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="right">{{.Value}}</h5>
           </td>
           </td>
         </tr>
         </tr>
         {{end}}
         {{end}}
@@ -267,17 +265,17 @@ text-decoration: underline;
 </table>
 </table>
 {{end}}
 {{end}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-    <tr style="padding: 0; vertical-align: top;" align="left">
-    <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-      <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+    <tr style="vertical-align: top; padding: 0;" align="left">
+    <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+      <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
             {{if ne .ImageLink "" }}
             {{if ne .ImageLink "" }}
-              <img src="{{.ImageLink}}" alt="Alerting Panel" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: block; outline: none !important; text-decoration: none !important; width: auto;" align="left" />
+              <img src="{{.ImageLink}}" alt="Alerting Panel" style="outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; width: auto; clear: both; display: block; border: 0;" align="left" />
             {{end}}
             {{end}}
             {{if ne .EmbededImage "" }}
             {{if ne .EmbededImage "" }}
-              <img src="cid:{{.EmbededImage}}" alt="Alerting Panel" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: block; outline: none !important; text-decoration: none !important; width: auto;" align="left" />
+              <img src="cid:{{.EmbededImage}}" alt="Alerting Panel" style="outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; width: auto; clear: both; display: block; border: 0;" align="left" />
             {{end}}
             {{end}}
           </td>
           </td>
         </tr>
         </tr>
@@ -287,25 +285,25 @@ text-decoration: underline;
 </table>
 </table>
 
 
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-  <tr style="padding: 0; vertical-align: top;" align="left">
-    <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-      <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-        <tr style="padding: 0; vertical-align: top;" align="left">
-          <td class="center six" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 50%; word-break: break-word;" align="center" valign="top">
-            <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 20px; margin-top: 10px; padding: 0; text-align: left; vertical-align: top;">
-              <tr style="padding: 0; vertical-align: top;" align="left">
-                <td align="center" class="better-button" bgcolor="#ff8f2b" style="-moz-border-radius: 2px; -moz-hyphens: auto; -webkit-border-radius: 2px; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; border-radius: 2px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px; word-break: break-word;" valign="top">
-                  <a href="{{.RuleUrl}}" target="_blank" style="-moz-border-radius: 2px; -webkit-border-radius: 2px; border: 1px solid #ff8f2b; border-radius: 2px; color: #FFF; display: inline-block; padding: 12px 25px; text-decoration: none;">View your Alert rule</a>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+  <tr style="vertical-align: top; padding: 0;" align="left">
+    <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+      <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+        <tr style="vertical-align: top; padding: 0;" align="left">
+          <td class="center six" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 50%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+            <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; margin-top: 10px; margin-bottom: 20px; padding: 0;">
+              <tr style="vertical-align: top; padding: 0;" align="left">
+                <td align="center" class="better-button" bgcolor="#ff8f2b" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; margin: 0; padding: 0px;" valign="top">
+                  <a href="{{.RuleUrl}}" target="_blank" style="color: #FFF; text-decoration: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; display: inline-block; padding: 12px 25px; border: 1px solid #ff8f2b;">View your Alert rule</a>
                 </td>
                 </td>
               </tr>
               </tr>
             </table>
             </table>
             </td>
             </td>
-            <td class="center six" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 50%; word-break: break-word;" align="center" valign="top">
-            <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 20px; margin-top: 10px; padding: 0; text-align: left; vertical-align: top;">
-              <tr style="padding: 0; vertical-align: top;" align="left">
-                <td align="center" class="better-button-alt" bgcolor="#efefef" style="-moz-border-radius: 2px; -moz-hyphens: auto; -webkit-border-radius: 2px; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; border-radius: 2px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px; word-break: break-word;" valign="top">
-                  <a href="{{.AlertPageUrl}}" target="_blank" style="-moz-border-radius: 2px; -webkit-border-radius: 2px; background: #EFEFEF; border: 1px solid #ff8f2b; border-radius: 2px; color: #ff8f2b; display: inline-block; padding: 12px 25px; text-decoration: none;"> Go to the Alerts page</a>
+            <td class="center six" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 50%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+            <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; margin-top: 10px; margin-bottom: 20px; padding: 0;">
+              <tr style="vertical-align: top; padding: 0;" align="left">
+                <td align="center" class="better-button-alt" bgcolor="#efefef" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; margin: 0; padding: 0px;" valign="top">
+                  <a href="{{.AlertPageUrl}}" target="_blank" style="color: #ff8f2b; text-decoration: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; display: inline-block; background-color: #EFEFEF; padding: 12px 25px; border: 1px solid #ff8f2b;"> Go to the Alerts page</a>
                 </td>
                 </td>
               </tr>
               </tr>
             </table>
             </table>
@@ -323,20 +321,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 57 - 59
public/emails/invited_to_org.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,26 +198,26 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								
 								
 
 
 {{Subject .Subject "{{.InvitedBy}} has added you to the {{.OrgName}} organization"}}
 {{Subject .Subject "{{.InvitedBy}} has added you to the {{.OrgName}} organization"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
-						<h4 class="center" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 20px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="center">You have been added to {{.OrgName}}</h4>
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+						<h4 class="center" style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 20px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="center">You have been added to {{.OrgName}}</h4>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 
 
@@ -227,22 +225,22 @@ text-decoration: underline;
 	</tr>
 	</tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left"><b>{{.InvitedBy}}</b> has added you to the <b>{{.OrgName}}</b> organization in Grafana.
-						</p><p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">Once logged in, {{.OrgName}} will be available in the left side menu, in the dropdown below your username.</p>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left"><b>{{.InvitedBy}}</b> has added you to the <b>{{.OrgName}}</b> organization in Grafana.
+						</p><p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">Once logged in, {{.OrgName}} will be available in the left side menu, in the dropdown below your username.</p>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 20px; margin-top: 10px; padding: 0; text-align: left; vertical-align: top;">
-							<tr style="padding: 0; vertical-align: top;" align="left">
-								<td align="center" class="better-button" bgcolor="#ff8f2b" style="-moz-border-radius: 2px; -moz-hyphens: auto; -webkit-border-radius: 2px; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; border-radius: 2px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px; word-break: break-word;" valign="top"><a href="{{.AppUrl}}" target="_blank" style="-moz-border-radius: 2px; -webkit-border-radius: 2px; border: 1px solid #ff8f2b; border-radius: 2px; color: #FFF; display: inline-block; padding: 12px 25px; text-decoration: none;">Log in now</a></td>
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; margin-top: 10px; margin-bottom: 20px; padding: 0;">
+							<tr style="vertical-align: top; padding: 0;" align="left">
+								<td align="center" class="better-button" bgcolor="#ff8f2b" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; margin: 0; padding: 0px;" valign="top"><a href="{{.AppUrl}}" target="_blank" style="color: #FFF; text-decoration: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; display: inline-block; padding: 12px 25px; border: 1px solid #ff8f2b;">Log in now</a></td>
 							</tr>
 							</tr>
 						</table>
 						</table>
 					</td>
 					</td>
@@ -259,20 +257,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 59 - 61
public/emails/new_user_invite.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,26 +198,26 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								
 								
 
 
 {{Subject .Subject "{{.InvitedBy}} has invited you to join Grafana"}}
 {{Subject .Subject "{{.InvitedBy}} has invited you to join Grafana"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
-						<h4 class="center" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 20px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="center">You're invited to join {{.OrgName}}</h4>
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+						<h4 class="center" style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 20px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="center">You're invited to join {{.OrgName}}</h4>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 
 
@@ -227,29 +225,29 @@ text-decoration: underline;
 	</tr>
 	</tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">You've been invited to join the <b>{{.OrgName}}</b> organization by <b>{{.InvitedBy}}</b>. To accept your invitation and join the team, please click the link below:</p>
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">You've been invited to join the <b>{{.OrgName}}</b> organization by <b>{{.InvitedBy}}</b>. To accept your invitation and join the team, please click the link below:</p>
 					</td>
 					</td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">				
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-	                    <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 20px; margin-top: 10px; padding: 0; text-align: left; vertical-align: top;">
-	                    	<tr style="padding: 0; vertical-align: top;" align="left">
-	                          <td align="center" class="better-button" bgcolor="#ff8f2b" style="-moz-border-radius: 2px; -moz-hyphens: auto; -webkit-border-radius: 2px; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; border-radius: 2px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px; word-break: break-word;" valign="top"><a href="{{.LinkUrl}}" target="_blank" style="-moz-border-radius: 2px; -webkit-border-radius: 2px; border: 1px solid #ff8f2b; border-radius: 2px; color: #FFF; display: inline-block; padding: 12px 25px; text-decoration: none;">Accept Invitation</a></td>
+				<tr style="vertical-align: top; padding: 0;" align="left">				
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+	                    <table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; margin-top: 10px; margin-bottom: 20px; padding: 0;">
+	                    	<tr style="vertical-align: top; padding: 0;" align="left">
+	                          <td align="center" class="better-button" bgcolor="#ff8f2b" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; margin: 0; padding: 0px;" valign="top"><a href="{{.LinkUrl}}" target="_blank" style="color: #FFF; text-decoration: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; display: inline-block; padding: 12px 25px; border: 1px solid #ff8f2b;">Accept Invitation</a></td>
 	                        </tr>
 	                        </tr>
 	                    </table>
 	                    </table>
 					</td>
 					</td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">You can also copy/paste this link into your browser directly: <a href="{{.LinkUrl}}" style="color: #E67612; text-decoration: none;">{{.LinkUrl}}</a></p>
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">You can also copy/paste this link into your browser directly: <a href="{{.LinkUrl}}" style="color: #E67612; text-decoration: none;">{{.LinkUrl}}</a></p>
 					</td>								
 					</td>								
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 		</td>
 		</td>
@@ -260,20 +258,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 53 - 55
public/emails/reset_password.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,24 +198,24 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								{{Subject .Subject "Reset your Grafana password - {{.Name}}"}}
 								{{Subject .Subject "Reset your Grafana password - {{.Name}}"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
-						<h4 style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 20px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="left">Hi {{.Name}},</h4>
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+						<h4 style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 20px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left">Hi {{.Name}},</h4>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 
 
@@ -225,21 +223,21 @@ text-decoration: underline;
 	</tr>
 	</tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">
 							Please click the following link to reset your password within <b>{{.EmailCodeValidHours}} hours</b>.
 							Please click the following link to reset your password within <b>{{.EmailCodeValidHours}} hours</b>.
 						</p>
 						</p>
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">
 							<a href="{{.AppUrl}}user/password/reset?code={{.Code}}" style="color: #E67612; text-decoration: none;">{{.AppUrl}}user/password/reset?code={{.Code}}</a>
 							<a href="{{.AppUrl}}user/password/reset?code={{.Code}}" style="color: #E67612; text-decoration: none;">{{.AppUrl}}user/password/reset?code={{.Code}}</a>
 						</p>
 						</p>
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">Not working? Try copying and pasting it to your browser.</p>
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">Not working? Try copying and pasting it to your browser.</p>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 
 
@@ -254,20 +252,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 56 - 58
public/emails/signup_started.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,24 +198,24 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								{{Subject .Subject "Welcome to Grafana, please complete your sign up!"}}
 								{{Subject .Subject "Welcome to Grafana, please complete your sign up!"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
-						<h4 class="center" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 20px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="center">Complete the signup</h4>
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+						<h4 class="center" style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 20px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="center">Complete the signup</h4>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
 			</table>
 			</table>
 
 
@@ -225,23 +223,23 @@ text-decoration: underline;
 	</tr>
 	</tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
 						Copy and past the email verification code:<br />
 						Copy and past the email verification code:<br />
-						<span class="verification-code" style="background: #EEEEEE; display: inline-block; font-size: 20px; font-weight: bold; margin: 8px; padding: 3px;">{{.Code}}</span><br /> in
+						<span class="verification-code" style="background-color: #EEEEEE; display: inline-block; font-weight: bold; font-size: 20px; margin: 8px; padding: 3px;">{{.Code}}</span><br /> in
 						the sign up form <strong>or</strong> use the link below.
 						the sign up form <strong>or</strong> use the link below.
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 20px; margin-top: 10px; padding: 0; text-align: left; vertical-align: top;">
-							<tr style="padding: 0; vertical-align: top;" align="left">
-								<td align="center" class="better-button" bgcolor="#ff8f2b" style="-moz-border-radius: 2px; -moz-hyphens: auto; -webkit-border-radius: 2px; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; border-radius: 2px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px; word-break: break-word;" valign="top"><a href="{{.SignUpUrl}}" target="_blank" style="-moz-border-radius: 2px; -webkit-border-radius: 2px; border: 1px solid #ff8f2b; border-radius: 2px; color: #FFF; display: inline-block; padding: 12px 25px; text-decoration: none;">Complete Sign Up</a></td>
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<table class="better-button" align="center" border="0" cellspacing="0" cellpadding="0" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; margin-top: 10px; margin-bottom: 20px; padding: 0;">
+							<tr style="vertical-align: top; padding: 0;" align="left">
+								<td align="center" class="better-button" bgcolor="#ff8f2b" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; margin: 0; padding: 0px;" valign="top"><a href="{{.SignUpUrl}}" target="_blank" style="color: #FFF; text-decoration: none; -webkit-border-radius: 2px; -moz-border-radius: 2px; border-radius: 2px; display: inline-block; padding: 12px 25px; border: 1px solid #ff8f2b;">Complete Sign Up</a></td>
 							</tr>
 							</tr>
 						</table>
 						</table>
 					</td>
 					</td>
@@ -258,20 +256,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 56 - 58
public/emails/welcome_on_signup.html

@@ -4,9 +4,7 @@
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 	<meta name="viewport" content="width=device-width" />
 	<meta name="viewport" content="width=device-width" />
 	
 	
-</head>
-<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="-ms-text-size-adjust: 100%; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100% !important; line-height: 19px; margin: 0 auto; min-width: 100%; padding: 0; text-align: left; width: 100% !important;" bgcolor="#2e2e2e"><style type="text/css">
-body {
+<style>body {
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 width: 100% !important; min-width: 100%; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; margin: 0; padding: 0;
 }
 }
 img {
 img {
@@ -166,29 +164,29 @@ text-decoration: underline;
     width: 270px;
     width: 270px;
   }
   }
 }
 }
-</style>
-
-	<table class="body" style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; border-collapse: collapse; border-spacing: 0; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; height: 100%; line-height: 19px; margin: 0; padding: 0; text-align: left; vertical-align: top; width: 100%;" bgcolor="#2e2e2e">
-		<tr style="padding: 0; vertical-align: top;" align="left">
-			<td class="center" align="center" valign="top" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;">
-        		<center style="min-width: 580px; width: 100%;">
+</style></head>
+<body leftmargin="0" topmargin="0" marginwidth="0" marginheight="0" class="main" style="height: 100% !important; width: 100% !important; min-width: 100%; -webkit-text-size-adjust: none; -ms-text-size-adjust: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; text-align: left; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; margin: 0 auto; padding: 0;" bgcolor="#2e2e2e">
 
 
-					<table class="row header" style="border-collapse: collapse; border-spacing: 0; margin-bottom: 25px; margin-top: 25px; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-						  <td class="center" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; word-break: break-word;" valign="top">
-						    <center style="min-width: 580px; width: 100%;">
+	<table class="body" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; height: 100%; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" bgcolor="#2e2e2e">
+		<tr style="vertical-align: top; padding: 0;" align="left">
+			<td class="center" align="center" valign="top" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;">
+        <center style="width: 100%; min-width: 580px;">
+					<table class="row header" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; margin-top: 25px; margin-bottom: 25px; padding: 0px;">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+						  <td class="center" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" valign="top">
+						    <center style="width: 100%; min-width: 580px;">
 
 
-						      <table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;">
-						        <tr style="padding: 0; vertical-align: top;" align="left">
-						          <td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+						      <table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;">
+						        <tr style="vertical-align: top; padding: 0;" align="left">
+						          <td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-						            <table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-						              <tr style="padding: 0; vertical-align: top;" align="left">
-						                <td class="six sub-columns center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; min-width: 0px; padding: 0px 10px 10px 0px; width: 50%; word-break: break-word;" align="center" valign="top">
-											<img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="-ms-interpolation-mode: bicubic; border: 0; clear: both; display: inline; outline: none !important; text-decoration: none !important; width: 200px;" align="none" />
-						                </td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
-						              </tr>
+						            <table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+						              <tr style="vertical-align: top; padding: 0;" align="left">
+						                <td class="twelve sub-columns center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; min-width: 0px; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 10px 10px 0px;" align="center" valign="top">
+                              <img class="logo" src="http://grafana.org/assets/img/logo_new_transparent_200x48.png" style="width: 200px; display: inline; outline: none !important; text-decoration: none !important; -ms-interpolation-mode: bicubic; clear: both; border: 0;" align="none" />
+                            </td>
+                            <td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
+                          </tr>
 						            </table>
 						            </table>
 
 
 						          </td>
 						          </td>
@@ -200,27 +198,27 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 
 
-					<table class="container" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: inherit; vertical-align: top; width: 580px;" width="600" bgcolor="#efefef">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td height="2" class="spacer mb-shorten" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; background: linear-gradient(to right, #ffed00 0%, #f26529 75%); border: 0; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 0; font-weight: normal; height: 2px !important; hyphens: auto; line-height: 0; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 0; word-break: break-word;" valign="top" align="left"> </td>
+					<table class="container" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: inherit; width: 580px; margin: 0 auto; padding: 0;" width="600" bgcolor="#efefef">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td height="2" class="spacer mb-shorten" style="font-size: 0; line-height: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; background-image: linear-gradient(to right, #ffed00 0%, #f26529 75%); height: 2px !important; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0; border: 0;" valign="top" align="left"> </td>
 						</tr>
 						</tr>
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="mini-centered-text" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #343b41; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif; hyphens: auto; margin: 0; mso-table-lspace: 0pt; mso-table-rspace: 0pt; padding: 25px 35px; word-break: break-word;" align="center" valign="top">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="mini-centered-text" style="color: #343b41; mso-table-lspace: 0pt; mso-table-rspace: 0pt; word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 25px 35px; font: 400 16px/27px 'Helvetica Neue', Helvetica, Arial, sans-serif;" align="center" valign="top">
 								{{Subject .Subject "Welcome to Grafana"}}
 								{{Subject .Subject "Welcome to Grafana"}}
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
 
 
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
-						<h4 style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 20px; font-weight: normal; line-height: 1.3; margin: 0; padding: 0; word-break: normal;" align="left">Hi {{.Name}},</h4>
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
+						<h4 style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 1.3; word-break: normal; font-size: 20px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left">Hi {{.Name}},</h4>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
 						Welcome! Ready to start building some beautiful metric and analytic dashboards?
 						Welcome! Ready to start building some beautiful metric and analytic dashboards?
 					</td>
 					</td>
 				</tr>
 				</tr>
@@ -230,23 +228,23 @@ text-decoration: underline;
 	</tr>
 	</tr>
 </table>
 </table>
 
 
-<table class="row" style="border-collapse: collapse; border-spacing: 0; display: block; padding: 0px; position: relative; text-align: left; vertical-align: top; width: 100%;">
-	<tr style="padding: 0; vertical-align: top;" align="left">
-		<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-			<table class="twelve columns" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: left; vertical-align: top; width: 580px;">
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td class="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="center" valign="top">
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">
+<table class="row" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 100%; position: relative; display: block; padding: 0px;">
+	<tr style="vertical-align: top; padding: 0;" align="left">
+		<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 0px 0px;" align="left" valign="top">
+			<table class="twelve columns" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: left; width: 580px; margin: 0 auto; padding: 0;">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td class="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="center" valign="top">
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">
 							If you are new to Grafana please read the <a href="http://docs.grafana.org/guides/gettingstarted/" style="color: #E67612; text-decoration: none;">Getting Started</a> guide.
 							If you are new to Grafana please read the <a href="http://docs.grafana.org/guides/gettingstarted/" style="color: #E67612; text-decoration: none;">Getting Started</a> guide.
 						</p>
 						</p>
 					</td>
 					</td>
-					<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+					<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 				</tr>
 				</tr>
-				<tr style="padding: 0; vertical-align: top;" align="left">
-					<td style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; word-break: break-word;" align="left" valign="top">
+				<tr style="vertical-align: top; padding: 0;" align="left">
+					<td style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" align="left" valign="top">
 						Thank you for joining our community.
 						Thank you for joining our community.
 						<br />
 						<br />
-						<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="left">The Grafana Team</p>
+						<p style="color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="left">The Grafana Team</p>
 					</td>
 					</td>
 				</tr>
 				</tr>
 			</table>
 			</table>
@@ -261,20 +259,20 @@ text-decoration: underline;
 						</tr>
 						</tr>
 					</table>
 					</table>
 					
 					
-					<table class="footer center" style="border-collapse: collapse; border-spacing: 0; color: #999999; margin-top: 20px; padding: 0; text-align: center; vertical-align: top;" bgcolor="#2e2e2e">
-						<tr style="padding: 0; vertical-align: top;" align="left">
-							<td class="wrapper last" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 10px 20px 0px 0px; position: relative; word-break: break-word;" align="left" valign="top">
-								<table class="twelve columns center" style="border-collapse: collapse; border-spacing: 0; margin: 0 auto; padding: 0; text-align: center; vertical-align: top; width: 580px;">
-									<tr style="padding: 0; vertical-align: top;" align="left">
-										<td class="twelve" align="center" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0px 0px 10px; width: 100%; word-break: break-word;" valign="top">
-											<center style="min-width: 580px; width: 100%;">
-												<p style="-webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 12px; font-weight: normal; line-height: 19px; margin: 0 0 10px; padding: 0;" align="center">
+					<table class="footer center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; color: #999999; margin-top: 20px; padding: 0;" bgcolor="#2e2e2e">
+						<tr style="vertical-align: top; padding: 0;" align="left">
+							<td class="wrapper last" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; position: relative; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 10px 20px 0px 0px;" align="left" valign="top">
+								<table class="twelve columns center" style="border-spacing: 0; border-collapse: collapse; vertical-align: top; text-align: center; width: 580px; margin: 0 auto; padding: 0;">
+									<tr style="vertical-align: top; padding: 0;" align="left">
+										<td class="twelve" align="center" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; width: 100%; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0px 0px 10px;" valign="top">
+											<center style="width: 100%; min-width: 580px;">
+												<p style="font-size: 12px; color: #999999; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0 0 10px; padding: 0;" align="center">
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													Sent by <a href="{{.AppUrl}}" style="color: #E67612; text-decoration: none;">Grafana v{{.BuildVersion}}</a>
 													<br />© 2016 Grafana and raintank
 													<br />© 2016 Grafana and raintank
 												</p>
 												</p>
 											</center>
 											</center>
 										</td>
 										</td>
-										<td class="expander" style="-moz-hyphens: auto; -webkit-font-smoothing: antialiased; -webkit-hyphens: auto; -webkit-text-size-adjust: none; border-collapse: collapse !important; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-size: 14px; font-weight: normal; hyphens: auto; line-height: 19px; margin: 0; padding: 0; visibility: hidden; width: 0px; word-break: break-word;" align="left" valign="top"></td>
+										<td class="expander" style="word-break: break-word; -webkit-hyphens: auto; -moz-hyphens: auto; hyphens: auto; border-collapse: collapse !important; visibility: hidden; width: 0px; color: #222222; font-family: 'Open Sans', 'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif; font-weight: normal; line-height: 19px; font-size: 14px; -webkit-font-smoothing: antialiased; -webkit-text-size-adjust: none; margin: 0; padding: 0;" align="left" valign="top"></td>
 									</tr>
 									</tr>
 								</table>
 								</table>
 							</td>
 							</td>

+ 15 - 3
public/sass/pages/_alerting.scss

@@ -50,9 +50,8 @@
 
 
 .panel-alert-state {
 .panel-alert-state {
   &--alerting {
   &--alerting {
-    animation: alerting-panel 1.6s cubic-bezier(1,.1,.73,1) 0s infinite alternate;
     box-shadow: 0 0 10px rgba($critical,0.5);
     box-shadow: 0 0 10px rgba($critical,0.5);
-    opacity: 1;
+    position: relative;
 
 
     .panel-alert-icon:before {
     .panel-alert-icon:before {
       color: $critical;
       color: $critical;
@@ -60,6 +59,19 @@
     }
     }
   }
   }
 
 
+  &--alerting::after {
+    content: '';
+    position: absolute;
+    top: 0;
+    z-index: -1;
+    width: 100%;
+    height: 100%;
+    box-shadow: 0 0 10px rgba($critical,1);
+    opacity: 0;
+    animation: alerting-panel 1.6s cubic-bezier(1,.1,.73,1) 0s infinite alternate;
+  }
+
+
   &--ok {
   &--ok {
     .panel-alert-icon:before {
     .panel-alert-icon:before {
       color: $online;
       color: $online;
@@ -70,6 +82,6 @@
 
 
 @keyframes alerting-panel {
 @keyframes alerting-panel {
   100% {
   100% {
-    box-shadow: 0 0 15px $critical;
+    opacity: 1;
   }
   }
 }
 }

+ 3 - 3
public/sass/pages/_dashboard.scss

@@ -185,9 +185,9 @@ div.flot-text {
   box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 5px rgba(82,168,236,10.8)
   box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 5px rgba(82,168,236,10.8)
 }
 }
 
 
-.panel-hover-highlight  {
-  box-shadow: inset 0 1px 1px rgba(0,0,0,0.025), 0 0 1px rgba(82,168,236,0.5)
-}
+// .panel-hover-highlight  {
+//   box-shadow: inset 0 1px 1px rgba(0,0,0,0.025), 0 0 1px rgba(82,168,236,0.5)
+// }
 
 
 .on-drag-hover {
 .on-drag-hover {
   .panel-container {
   .panel-container {

+ 1 - 0
public/test/test-main.js

@@ -40,6 +40,7 @@
       "jquery.flot.fillbelow": "vendor/flot/jquery.flot.fillbelow",
       "jquery.flot.fillbelow": "vendor/flot/jquery.flot.fillbelow",
       "jquery.flot.gauge": "vendor/flot/jquery.flot.gauge",
       "jquery.flot.gauge": "vendor/flot/jquery.flot.gauge",
       "d3": "vendor/d3/d3.js",
       "d3": "vendor/d3/d3.js",
+      "jquery.flot.dashes": "vendor/flot/jquery.flot.dashes"
     },
     },
 
 
     packages: {
     packages: {

+ 236 - 0
public/vendor/flot/jquery.flot.dashes.js

@@ -0,0 +1,236 @@
+/*
+ * jQuery.flot.dashes
+ *
+ * options = {
+ *   series: {
+ *     dashes: {
+ *
+ *       // show
+ *       // default: false
+ *       // Whether to show dashes for the series.
+ *       show: <boolean>,
+ *
+ *       // lineWidth
+ *       // default: 2
+ *       // The width of the dashed line in pixels.
+ *       lineWidth: <number>,
+ *
+ *       // dashLength
+ *       // default: 10
+ *       // Controls the length of the individual dashes and the amount of
+ *       // space between them.
+ *       // If this is a number, the dashes and spaces will have that length.
+ *       // If this is an array, it is read as [ dashLength, spaceLength ]
+ *       dashLength: <number> or <array[2]>
+ *     }
+ *   }
+ * }
+ */
+(function($){
+
+  function init(plot) {
+
+    plot.hooks.processDatapoints.push(function(plot, series, datapoints) {
+
+      if (!series.dashes.show) return;
+
+      plot.hooks.draw.push(function(plot, ctx) {
+
+        var plotOffset = plot.getPlotOffset(),
+          axisx = series.xaxis,
+          axisy = series.yaxis;
+
+        function plotDashes(xoffset, yoffset) {
+
+          var points = datapoints.points,
+            ps = datapoints.pointsize,
+            prevx = null,
+            prevy = null,
+            dashRemainder = 0,
+            dashOn = true,
+            dashOnLength,
+            dashOffLength;
+
+          if (series.dashes.dashLength[0]) {
+            dashOnLength = series.dashes.dashLength[0];
+            if (series.dashes.dashLength[1]) {
+              dashOffLength = series.dashes.dashLength[1];
+            } else {
+              dashOffLength = dashOnLength;
+            }
+          } else {
+            dashOffLength = dashOnLength = series.dashes.dashLength;
+          }
+
+          ctx.beginPath();
+
+          for (var i = ps; i < points.length; i += ps) {
+
+            var x1 = points[i - ps],
+              y1 = points[i - ps + 1],
+              x2 = points[i],
+              y2 = points[i + 1];
+
+            if (x1 == null || x2 == null) continue;
+
+            // clip with ymin
+            if (y1 <= y2 && y1 < axisy.min) {
+              if (y2 < axisy.min) continue;   // line segment is outside
+              // compute new intersection point
+              x1 = (axisy.min - y1) / (y2 - y1) * (x2 - x1) + x1;
+              y1 = axisy.min;
+            } else if (y2 <= y1 && y2 < axisy.min) {
+              if (y1 < axisy.min) continue;
+              x2 = (axisy.min - y1) / (y2 - y1) * (x2 - x1) + x1;
+              y2 = axisy.min;
+            }
+
+            // clip with ymax
+            if (y1 >= y2 && y1 > axisy.max) {
+              if (y2 > axisy.max) continue;
+              x1 = (axisy.max - y1) / (y2 - y1) * (x2 - x1) + x1;
+              y1 = axisy.max;
+            } else if (y2 >= y1 && y2 > axisy.max) {
+              if (y1 > axisy.max) continue;
+              x2 = (axisy.max - y1) / (y2 - y1) * (x2 - x1) + x1;
+              y2 = axisy.max;
+            }
+
+            // clip with xmin
+            if (x1 <= x2 && x1 < axisx.min) {
+              if (x2 < axisx.min) continue;
+              y1 = (axisx.min - x1) / (x2 - x1) * (y2 - y1) + y1;
+              x1 = axisx.min;
+            } else if (x2 <= x1 && x2 < axisx.min) {
+              if (x1 < axisx.min) continue;
+              y2 = (axisx.min - x1) / (x2 - x1) * (y2 - y1) + y1;
+              x2 = axisx.min;
+            }
+
+            // clip with xmax
+            if (x1 >= x2 && x1 > axisx.max) {
+              if (x2 > axisx.max) continue;
+              y1 = (axisx.max - x1) / (x2 - x1) * (y2 - y1) + y1;
+              x1 = axisx.max;
+            } else if (x2 >= x1 && x2 > axisx.max) {
+              if (x1 > axisx.max) continue;
+              y2 = (axisx.max - x1) / (x2 - x1) * (y2 - y1) + y1;
+              x2 = axisx.max;
+            }
+
+            if (x1 != prevx || y1 != prevy) {
+              ctx.moveTo(axisx.p2c(x1) + xoffset, axisy.p2c(y1) + yoffset);
+            }
+
+            var ax1 = axisx.p2c(x1) + xoffset,
+              ay1 = axisy.p2c(y1) + yoffset,
+              ax2 = axisx.p2c(x2) + xoffset,
+              ay2 = axisy.p2c(y2) + yoffset,
+              dashOffset;
+
+            function lineSegmentOffset(segmentLength) {
+
+              var c = Math.sqrt(Math.pow(ax2 - ax1, 2) + Math.pow(ay2 - ay1, 2));
+
+              if (c <= segmentLength) {
+                return {
+                  deltaX: ax2 - ax1,
+                  deltaY: ay2 - ay1,
+                  distance: c,
+                  remainder: segmentLength - c
+                }
+              } else {
+                var xsign = ax2 > ax1 ? 1 : -1,
+                  ysign = ay2 > ay1 ? 1 : -1;
+                return {
+                  deltaX: xsign * Math.sqrt(Math.pow(segmentLength, 2) / (1 + Math.pow((ay2 - ay1)/(ax2 - ax1), 2))),
+                  deltaY: ysign * Math.sqrt(Math.pow(segmentLength, 2) - Math.pow(segmentLength, 2) / (1 + Math.pow((ay2 - ay1)/(ax2 - ax1), 2))),
+                  distance: segmentLength,
+                  remainder: 0
+                };
+              }
+            }
+            //-end lineSegmentOffset
+
+            do {
+
+              dashOffset = lineSegmentOffset(
+                dashRemainder > 0 ? dashRemainder :
+                  dashOn ? dashOnLength : dashOffLength);
+
+              if (dashOffset.deltaX != 0 || dashOffset.deltaY != 0) {
+                if (dashOn) {
+                  ctx.lineTo(ax1 + dashOffset.deltaX, ay1 + dashOffset.deltaY);
+                } else {
+                  ctx.moveTo(ax1 + dashOffset.deltaX, ay1 + dashOffset.deltaY);
+                }
+              }
+
+              dashOn = !dashOn;
+              dashRemainder = dashOffset.remainder;
+              ax1 += dashOffset.deltaX;
+              ay1 += dashOffset.deltaY;
+
+            } while (dashOffset.distance > 0);
+
+            prevx = x2;
+            prevy = y2;
+          }
+
+          ctx.stroke();
+        }
+        //-end plotDashes
+
+        ctx.save();
+        ctx.translate(plotOffset.left, plotOffset.top);
+        ctx.lineJoin = 'round';
+
+        var lw = series.dashes.lineWidth,
+          sw = series.shadowSize;
+
+        // FIXME: consider another form of shadow when filling is turned on
+        if (lw > 0 && sw > 0) {
+          // draw shadow as a thick and thin line with transparency
+          ctx.lineWidth = sw;
+          ctx.strokeStyle = "rgba(0,0,0,0.1)";
+          // position shadow at angle from the mid of line
+          var angle = Math.PI/18;
+          plotDashes(Math.sin(angle) * (lw/2 + sw/2), Math.cos(angle) * (lw/2 + sw/2));
+          ctx.lineWidth = sw/2;
+          plotDashes(Math.sin(angle) * (lw/2 + sw/4), Math.cos(angle) * (lw/2 + sw/4));
+        }
+
+        ctx.lineWidth = lw;
+        ctx.strokeStyle = series.color;
+
+        if (lw > 0) {
+          plotDashes(0, 0);
+        }
+
+        ctx.restore();
+
+      });
+      //-end draw hook
+
+    });
+    //-end processDatapoints hook
+
+  }
+  //-end init
+
+  $.plot.plugins.push({
+    init: init,
+    options: {
+      series: {
+        dashes: {
+          show: false,
+          lineWidth: 2,
+          dashLength: 10
+        }
+      }
+    },
+    name: 'dashes',
+    version: '0.1'
+  });
+
+})(jQuery)

+ 0 - 24
vendor/github.com/Unknwon/com/.gitignore

@@ -1,24 +0,0 @@
-# Compiled Object files, Static and Dynamic libs (Shared Objects)
-*.o
-*.a
-*.so
-
-# Folders
-_obj
-_test
-.idea
-
-# Architecture specific extensions/prefixes
-*.[568vq]
-[568vq].out
-
-*.cgo1.go
-*.cgo2.c
-_cgo_defun.c
-_cgo_gotypes.go
-_cgo_export.*
-
-_testmain.go
-
-*.exe
-*.iml

+ 4 - 8
vendor/github.com/Unknwon/com/README.md

@@ -1,7 +1,7 @@
-Common functions
-===
+Common Functions
+================
 
 
-[![Build Status](https://drone.io/github.com/Unknwon/com/status.png)](https://drone.io/github.com/Unknwon/com/latest) [![Go Walker](http://gowalker.org/api/v1/badge)](http://gowalker.org/github.com/Unknwon/com)
+[![Build Status](https://travis-ci.org/Unknwon/com.svg)](https://travis-ci.org/Unknwon/com) [![Go Walker](http://gowalker.org/api/v1/badge)](http://gowalker.org/github.com/Unknwon/com)
 
 
 This is an open source project for commonly used functions for the Go programming language.
 This is an open source project for commonly used functions for the Go programming language.
 
 
@@ -17,8 +17,4 @@ Your contribute is welcome, but you have to check following steps after you adde
 2. Make sure you wrote test cases with any possible condition for **all functions** in file `*_test.go`.
 2. Make sure you wrote test cases with any possible condition for **all functions** in file `*_test.go`.
 3. Make sure you wrote benchmarks for **all functions** in file `*_test.go`.
 3. Make sure you wrote benchmarks for **all functions** in file `*_test.go`.
 4. Make sure you wrote useful examples for **all functions** in file `example_test.go`.
 4. Make sure you wrote useful examples for **all functions** in file `example_test.go`.
-5. Make sure you ran `go test -bench="."` and got **PASS** .
-
-## Performance
-
-See results on [drone.io](https://drone.io/github.com/Unknwon/com/latest) by `go test -bench="."`.
+5. Make sure you ran `go test` and got **PASS** .

+ 0 - 140
vendor/github.com/Unknwon/com/cmd_test.go

@@ -1,140 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"fmt"
-	"runtime"
-	"strings"
-	"testing"
-)
-
-func TestColorLogS(t *testing.T) {
-	if runtime.GOOS != "windows" {
-		// Trace + path.
-		cls := ColorLogS("[TRAC] Trace level test with path( %s )", "/path/to/somethere")
-		clsR := fmt.Sprintf(
-			"[\033[%dmTRAC%s] Trace level test with path(\033[%dm%s%s)",
-			Blue, EndColor, Yellow, "/path/to/somethere", EndColor)
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Error + error.
-		cls = ColorLogS("[ERRO] Error level test with error[ %s ]", "test error")
-		clsR = fmt.Sprintf(
-			"[\033[%dmERRO%s] Error level test with error[\033[%dm%s%s]",
-			Red, EndColor, Red, "test error", EndColor)
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Warning + highlight.
-		cls = ColorLogS("[WARN] Warnning level test with highlight # %s #", "special offer!")
-		clsR = fmt.Sprintf(
-			"[\033[%dmWARN%s] Warnning level test with highlight \033[%dm%s%s",
-			Magenta, EndColor, Gray, "special offer!", EndColor)
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Success.
-		cls = ColorLogS("[SUCC] Success level test")
-		clsR = fmt.Sprintf(
-			"[\033[%dmSUCC%s] Success level test",
-			Green, EndColor)
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Default.
-		cls = ColorLogS("[INFO] Default level test")
-		clsR = fmt.Sprintf(
-			"[INFO] Default level test")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-	} else {
-		// Trace + path.
-		cls := ColorLogS("[TRAC] Trace level test with path( %s )", "/path/to/somethere")
-		clsR := fmt.Sprintf(
-			"[TRAC] Trace level test with path(%s)",
-			"/path/to/somethere")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Error + error.
-		cls = ColorLogS("[ERRO] Error level test with error[ %s ]", "test error")
-		clsR = fmt.Sprintf(
-			"[ERRO] Error level test with error[%s]",
-			"test error")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Warning + highlight.
-		cls = ColorLogS("[WARN] Warnning level test with highlight # %s #", "special offer!")
-		clsR = fmt.Sprintf(
-			"[WARN] Warnning level test with highlight %s",
-			"special offer!")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Success.
-		cls = ColorLogS("[SUCC] Success level test")
-		clsR = fmt.Sprintf(
-			"[SUCC] Success level test")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-
-		// Default.
-		cls = ColorLogS("[INFO] Default level test")
-		clsR = fmt.Sprintf(
-			"[INFO] Default level test")
-		if cls != clsR {
-			t.Errorf("ColorLogS:\n Expect => %s\n Got => %s\n", clsR, cls)
-		}
-	}
-}
-
-func TestExecCmd(t *testing.T) {
-	stdout, stderr, err := ExecCmd("go", "help", "get")
-	if err != nil {
-		t.Errorf("ExecCmd:\n Expect => %v\n Got => %v\n", nil, err)
-	} else if len(stderr) != 0 {
-		t.Errorf("ExecCmd:\n Expect => %s\n Got => %s\n", "", stderr)
-	} else if !strings.HasPrefix(stdout, "usage: go get") {
-		t.Errorf("ExecCmd:\n Expect => %s\n Got => %s\n", "usage: go get", stdout)
-	}
-}
-
-func BenchmarkColorLogS(b *testing.B) {
-	log := fmt.Sprintf(
-		"[WARN] This is a tesing log that should be colored, path( %s ),"+
-			" highlight # %s #, error [ %s ].",
-		"path to somewhere", "highlighted content", "tesing error")
-	for i := 0; i < b.N; i++ {
-		ColorLogS(log)
-	}
-}
-
-func BenchmarkExecCmd(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		ExecCmd("go", "help", "get")
-	}
-}

+ 1 - 1
vendor/github.com/Unknwon/com/convert.go

@@ -32,7 +32,7 @@ func (f StrTo) Uint8() (uint8, error) {
 }
 }
 
 
 func (f StrTo) Int() (int, error) {
 func (f StrTo) Int() (int, error) {
-	v, err := strconv.ParseInt(f.String(), 10, 32)
+	v, err := strconv.ParseInt(f.String(), 10, 0)
 	return int(v), err
 	return int(v), err
 }
 }
 
 

+ 0 - 56
vendor/github.com/Unknwon/com/convert_test.go

@@ -1,56 +0,0 @@
-// Copyright 2014 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"testing"
-
-	. "github.com/smartystreets/goconvey/convey"
-)
-
-func TestHexStr2int(t *testing.T) {
-	Convey("Convert hex format string to decimal", t, func() {
-		hexDecs := map[string]int{
-			"1":   1,
-			"002": 2,
-			"011": 17,
-			"0a1": 161,
-			"35e": 862,
-		}
-
-		for hex, dec := range hexDecs {
-			val, err := HexStr2int(hex)
-			So(err, ShouldBeNil)
-			So(val, ShouldEqual, dec)
-		}
-	})
-}
-
-func TestInt2HexStr(t *testing.T) {
-	Convey("Convert decimal to hex format string", t, func() {
-		decHexs := map[int]string{
-			1:   "1",
-			2:   "2",
-			17:  "11",
-			161: "a1",
-			862: "35e",
-		}
-
-		for dec, hex := range decHexs {
-			val := Int2HexStr(dec)
-			So(val, ShouldEqual, hex)
-		}
-	})
-}

+ 0 - 58
vendor/github.com/Unknwon/com/dir_test.go

@@ -1,58 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"os"
-	"testing"
-
-	. "github.com/smartystreets/goconvey/convey"
-)
-
-func TestIsDir(t *testing.T) {
-	Convey("Check if given path is a directory", t, func() {
-		Convey("Pass a file name", func() {
-			So(IsDir("file.go"), ShouldEqual, false)
-		})
-		Convey("Pass a directory name", func() {
-			So(IsDir("testdata"), ShouldEqual, true)
-		})
-		Convey("Pass a invalid path", func() {
-			So(IsDir("foo"), ShouldEqual, false)
-		})
-	})
-}
-
-func TestCopyDir(t *testing.T) {
-	Convey("Items of two slices should be same", t, func() {
-		s1, err := StatDir("testdata", true)
-		So(err, ShouldEqual, nil)
-
-		err = CopyDir("testdata", "testdata2")
-		So(err, ShouldEqual, nil)
-
-		s2, err := StatDir("testdata2", true)
-		os.RemoveAll("testdata2")
-		So(err, ShouldEqual, nil)
-
-		So(CompareSliceStr(s1, s2), ShouldEqual, true)
-	})
-}
-
-func BenchmarkIsDir(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsDir("file.go")
-	}
-}

+ 0 - 299
vendor/github.com/Unknwon/com/example_test.go

@@ -1,299 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com_test
-
-import (
-	"fmt"
-	"io/ioutil"
-	"net/http"
-
-	"github.com/Unknwon/com"
-)
-
-// ------------------------------
-// cmd.go
-// ------------------------------
-
-func ExampleColorLogS() {
-	coloredLog := com.ColorLogS(fmt.Sprintf(
-		"[WARN] This is a tesing log that should be colored, path( %s ),"+
-			" highlight # %s #, error [ %s ].",
-		"path to somewhere", "highlighted content", "tesing error"))
-	fmt.Println(coloredLog)
-}
-
-func ExampleColorLog() {
-	com.ColorLog(fmt.Sprintf(
-		"[WARN] This is a tesing log that should be colored, path( %s ),"+
-			" highlight # %s #, error [ %s ].",
-		"path to somewhere", "highlighted content", "tesing error"))
-}
-
-func ExampleExecCmd() {
-	stdout, stderr, err := com.ExecCmd("go", "help", "get")
-	fmt.Println(stdout, stderr, err)
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// html.go
-// ------------------------------
-
-func ExampleHtml2JS() {
-	htm := "<div id=\"button\" class=\"btn\">Click me</div>\n\r"
-	js := string(com.Html2JS([]byte(htm)))
-	fmt.Println(js)
-	// Output: <div id=\"button\" class=\"btn\">Click me</div>\n
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// path.go
-// ------------------------------
-
-func ExampleGetGOPATHs() {
-	gps := com.GetGOPATHs()
-	fmt.Println(gps)
-}
-
-func ExampleGetSrcPath() {
-	srcPath, err := com.GetSrcPath("github.com/Unknwon/com")
-	if err != nil {
-		fmt.Println(err)
-		return
-	}
-	fmt.Println(srcPath)
-}
-
-func ExampleHomeDir() {
-	hd, err := com.HomeDir()
-	fmt.Println(hd, err)
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// file.go
-// ------------------------------
-
-func ExampleIsFile() {
-	if com.IsFile("file.go") {
-		fmt.Println("file.go exists")
-		return
-	}
-	fmt.Println("file.go is not a file or does not exist")
-}
-
-func ExampleIsExist() {
-	if com.IsExist("file.go") {
-		fmt.Println("file.go exists")
-		return
-	}
-	fmt.Println("file.go does not exist")
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// dir.go
-// ------------------------------
-
-func ExampleIsDir() {
-	if com.IsDir("files") {
-		fmt.Println("directory 'files' exists")
-		return
-	}
-	fmt.Println("'files' is not a directory or does not exist")
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// string.go
-// ------------------------------
-
-func ExampleIsLetter() {
-	fmt.Println(com.IsLetter('1'))
-	fmt.Println(com.IsLetter('['))
-	fmt.Println(com.IsLetter('a'))
-	fmt.Println(com.IsLetter('Z'))
-	// Output:
-	// false
-	// false
-	// true
-	// true
-}
-
-func ExampleExpand() {
-	match := map[string]string{
-		"domain":    "gowalker.org",
-		"subdomain": "github.com",
-	}
-	s := "http://{domain}/{subdomain}/{0}/{1}"
-	fmt.Println(com.Expand(s, match, "Unknwon", "gowalker"))
-	// Output: http://gowalker.org/github.com/Unknwon/gowalker
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// http.go
-// ------------------------------
-
-func ExampleHttpGet() ([]byte, error) {
-	rc, err := com.HttpGet(&http.Client{}, "http://gowalker.org", nil)
-	if err != nil {
-		return nil, err
-	}
-	p, err := ioutil.ReadAll(rc)
-	rc.Close()
-	return p, err
-}
-
-func ExampleHttpGetBytes() ([]byte, error) {
-	p, err := com.HttpGetBytes(&http.Client{}, "http://gowalker.org", nil)
-	return p, err
-}
-
-func ExampleHttpGetJSON() interface{} {
-	j := com.HttpGetJSON(&http.Client{}, "http://gowalker.org", nil)
-	return j
-}
-
-type rawFile struct {
-	name   string
-	rawURL string
-	data   []byte
-}
-
-func (rf *rawFile) Name() string {
-	return rf.name
-}
-
-func (rf *rawFile) RawUrl() string {
-	return rf.rawURL
-}
-
-func (rf *rawFile) Data() []byte {
-	return rf.data
-}
-
-func (rf *rawFile) SetData(p []byte) {
-	rf.data = p
-}
-
-func ExampleFetchFiles() {
-	// Code that should be outside of your function body.
-	// type rawFile struct {
-	// name   string
-	// 	rawURL string
-	// 	data   []byte
-	// }
-
-	// func (rf *rawFile) Name() string {
-	// 	return rf.name
-	// }
-
-	// func (rf *rawFile) RawUrl() string {
-	// 	return rf.rawURL
-	// }
-
-	// func (rf *rawFile) Data() []byte {
-	// 	return rf.data
-	// }
-
-	// func (rf *rawFile) SetData(p []byte) {
-	// 	rf.data = p
-	// }
-
-	files := []com.RawFile{
-		&rawFile{rawURL: "http://example.com"},
-		&rawFile{rawURL: "http://example.com/foo"},
-	}
-	err := com.FetchFiles(&http.Client{}, files, nil)
-	fmt.Println(err, len(files[0].Data()), len(files[1].Data()))
-}
-
-func ExampleFetchFilesCurl() {
-	// Code that should be outside of your function body.
-	// type rawFile struct {
-	// name   string
-	// 	rawURL string
-	// 	data   []byte
-	// }
-
-	// func (rf *rawFile) Name() string {
-	// 	return rf.name
-	// }
-
-	// func (rf *rawFile) RawUrl() string {
-	// 	return rf.rawURL
-	// }
-
-	// func (rf *rawFile) Data() []byte {
-	// 	return rf.data
-	// }
-
-	// func (rf *rawFile) SetData(p []byte) {
-	// 	rf.data = p
-	// }
-
-	files := []com.RawFile{
-		&rawFile{rawURL: "http://example.com"},
-		&rawFile{rawURL: "http://example.com/foo"},
-	}
-	err := com.FetchFilesCurl(files)
-	fmt.Println(err, len(files[0].Data()), len(files[1].Data()))
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// regex.go
-// ------------------------------
-
-func ExampleIsEmail() {
-	fmt.Println(com.IsEmail("test@example.com"))
-	fmt.Println(com.IsEmail("@example.com"))
-	// Output:
-	// true
-	// false
-}
-
-func ExampleIsUrl() {
-	fmt.Println(com.IsUrl("http://example.com"))
-	fmt.Println(com.IsUrl("http//example.com"))
-	// Output:
-	// true
-	// false
-}
-
-// ------------- END ------------
-
-// ------------------------------
-// slice.go
-// ------------------------------
-
-func ExampleAppendStr() {
-	s := []string{"a"}
-	s = com.AppendStr(s, "a")
-	s = com.AppendStr(s, "b")
-	fmt.Println(s)
-	// Output: [a b]
-}
-
-// ------------- END ------------

+ 0 - 61
vendor/github.com/Unknwon/com/file_test.go

@@ -1,61 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"testing"
-
-	. "github.com/smartystreets/goconvey/convey"
-)
-
-func TestIsFile(t *testing.T) {
-	if !IsFile("file.go") {
-		t.Errorf("IsExist:\n Expect => %v\n Got => %v\n", true, false)
-	}
-
-	if IsFile("testdata") {
-		t.Errorf("IsExist:\n Expect => %v\n Got => %v\n", false, true)
-	}
-
-	if IsFile("files.go") {
-		t.Errorf("IsExist:\n Expect => %v\n Got => %v\n", false, true)
-	}
-}
-
-func TestIsExist(t *testing.T) {
-	Convey("Check if file or directory exists", t, func() {
-		Convey("Pass a file name that exists", func() {
-			So(IsExist("file.go"), ShouldEqual, true)
-		})
-		Convey("Pass a directory name that exists", func() {
-			So(IsExist("testdata"), ShouldEqual, true)
-		})
-		Convey("Pass a directory name that does not exist", func() {
-			So(IsExist(".hg"), ShouldEqual, false)
-		})
-	})
-}
-
-func BenchmarkIsFile(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsFile("file.go")
-	}
-}
-
-func BenchmarkIsExist(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsExist("file.go")
-	}
-}

+ 0 - 35
vendor/github.com/Unknwon/com/html_test.go

@@ -1,35 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"testing"
-)
-
-func TestHtml2JS(t *testing.T) {
-	htm := "<div id=\"button\" class=\"btn\">Click me</div>\n\r"
-	js := string(Html2JS([]byte(htm)))
-	jsR := `<div id=\"button\" class=\"btn\">Click me</div>\n`
-	if js != jsR {
-		t.Errorf("Html2JS:\n Expect => %s\n Got => %s\n", jsR, js)
-	}
-}
-
-func BenchmarkHtml2JS(b *testing.B) {
-	htm := "<div id=\"button\" class=\"btn\">Click me</div>\n\r"
-	for i := 0; i < b.N; i++ {
-		Html2JS([]byte(htm))
-	}
-}

+ 0 - 111
vendor/github.com/Unknwon/com/http_test.go

@@ -1,111 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"io/ioutil"
-	"net/http"
-	"strings"
-	"testing"
-)
-
-var examplePrefix = `<!doctype html>
-<html>
-<head>
-    <title>Example Domain</title>
-`
-
-func TestHttpGet(t *testing.T) {
-	// 200.
-	rc, err := HttpGet(&http.Client{}, "http://example.com", nil)
-	if err != nil {
-		t.Fatalf("HttpGet:\n Expect => %v\n Got => %s\n", nil, err)
-	}
-	p, err := ioutil.ReadAll(rc)
-	if err != nil {
-		t.Errorf("HttpGet:\n Expect => %v\n Got => %s\n", nil, err)
-	}
-	s := string(p)
-	if !strings.HasPrefix(s, examplePrefix) {
-		t.Errorf("HttpGet:\n Expect => %s\n Got => %s\n", examplePrefix, s)
-	}
-}
-
-func TestHttpGetBytes(t *testing.T) {
-	p, err := HttpGetBytes(&http.Client{}, "http://example.com", nil)
-	if err != nil {
-		t.Errorf("HttpGetBytes:\n Expect => %v\n Got => %s\n", nil, err)
-	}
-	s := string(p)
-	if !strings.HasPrefix(s, examplePrefix) {
-		t.Errorf("HttpGet:\n Expect => %s\n Got => %s\n", examplePrefix, s)
-	}
-}
-
-func TestHttpGetJSON(t *testing.T) {
-
-}
-
-type rawFile struct {
-	name   string
-	rawURL string
-	data   []byte
-}
-
-func (rf *rawFile) Name() string {
-	return rf.name
-}
-
-func (rf *rawFile) RawUrl() string {
-	return rf.rawURL
-}
-
-func (rf *rawFile) Data() []byte {
-	return rf.data
-}
-
-func (rf *rawFile) SetData(p []byte) {
-	rf.data = p
-}
-
-func TestFetchFiles(t *testing.T) {
-	files := []RawFile{
-		&rawFile{rawURL: "http://example.com"},
-		&rawFile{rawURL: "http://example.com"},
-	}
-	err := FetchFiles(&http.Client{}, files, nil)
-	if err != nil {
-		t.Errorf("FetchFiles:\n Expect => %v\n Got => %s\n", nil, err)
-	} else if len(files[0].Data()) != 1270 {
-		t.Errorf("FetchFiles:\n Expect => %d\n Got => %d\n", 1270, len(files[0].Data()))
-	} else if len(files[1].Data()) != 1270 {
-		t.Errorf("FetchFiles:\n Expect => %d\n Got => %d\n", 1270, len(files[1].Data()))
-	}
-}
-
-func TestFetchFilesCurl(t *testing.T) {
-	files := []RawFile{
-		&rawFile{rawURL: "http://example.com"},
-		&rawFile{rawURL: "http://example.com"},
-	}
-	err := FetchFilesCurl(files)
-	if err != nil {
-		t.Errorf("FetchFilesCurl:\n Expect => %v\n Got => %s\n", nil, err)
-	} else if len(files[0].Data()) != 1270 {
-		t.Errorf("FetchFilesCurl:\n Expect => %d\n Got => %d\n", 1270, len(files[0].Data()))
-	} else if len(files[1].Data()) != 1270 {
-		t.Errorf("FetchFilesCurl:\n Expect => %d\n Got => %d\n", 1270, len(files[1].Data()))
-	}
-}

+ 10 - 5
vendor/github.com/Unknwon/com/math.go

@@ -14,11 +14,16 @@
 
 
 package com
 package com
 
 
-// PowInt is int type of math.Pow function.
+// PowInt is int type of math.Pow function. 
 func PowInt(x int, y int) int {
 func PowInt(x int, y int) int {
-	num := 1
-	for i := 0; i < y; i++ {
-		num *= x
+	if y <= 0 {
+		return 1
+	} else {
+		if y % 2 == 0 {
+			sqrt := PowInt(x, y/2)
+			return sqrt * sqrt
+		} else {
+			return PowInt(x, y-1) * x
+		}
 	}
 	}
-	return num
 }
 }

+ 3 - 3
vendor/github.com/Unknwon/com/path.go

@@ -64,9 +64,9 @@ func GetSrcPath(importPath string) (appPath string, err error) {
 // it returns error when the variable does not exist.
 // it returns error when the variable does not exist.
 func HomeDir() (home string, err error) {
 func HomeDir() (home string, err error) {
 	if runtime.GOOS == "windows" {
 	if runtime.GOOS == "windows" {
-		home = os.Getenv("HOMEDRIVE") + os.Getenv("HOMEPATH")
-		if home == "" {
-			home = os.Getenv("USERPROFILE")
+		home = os.Getenv("USERPROFILE")
+		if len(home) == 0 {
+			home = os.Getenv("HOMEDRIVE") + os.Getenv("HOMEPATH")
 		}
 		}
 	} else {
 	} else {
 		home = os.Getenv("HOME")
 		home = os.Getenv("HOME")

+ 0 - 67
vendor/github.com/Unknwon/com/path_test.go

@@ -1,67 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"os"
-	"runtime"
-	"testing"
-)
-
-func TestGetGOPATHs(t *testing.T) {
-	var gpsR []string
-
-	if runtime.GOOS != "windows" {
-		gpsR = []string{"path/to/gopath1", "path/to/gopath2", "path/to/gopath3"}
-		os.Setenv("GOPATH", "path/to/gopath1:path/to/gopath2:path/to/gopath3")
-	} else {
-		gpsR = []string{"path/to/gopath1", "path/to/gopath2", "path/to/gopath3"}
-		os.Setenv("GOPATH", "path\\to\\gopath1;path\\to\\gopath2;path\\to\\gopath3")
-	}
-
-	gps := GetGOPATHs()
-	if !CompareSliceStr(gps, gpsR) {
-		t.Errorf("GetGOPATHs:\n Expect => %s\n Got => %s\n", gpsR, gps)
-	}
-}
-
-func TestGetSrcPath(t *testing.T) {
-
-}
-
-func TestHomeDir(t *testing.T) {
-	_, err := HomeDir()
-	if err != nil {
-		t.Errorf("HomeDir:\n Expect => %v\n Got => %s\n", nil, err)
-	}
-}
-
-func BenchmarkGetGOPATHs(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		GetGOPATHs()
-	}
-}
-
-func BenchmarkGetSrcPath(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		GetSrcPath("github.com/Unknwon/com")
-	}
-}
-
-func BenchmarkHomeDir(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		HomeDir()
-	}
-}

+ 0 - 70
vendor/github.com/Unknwon/com/regex_test.go

@@ -1,70 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"testing"
-)
-
-func TestIsEmail(t *testing.T) {
-	emails := map[string]bool{
-		`test@example.com`:             true,
-		`single-character@b.org`:       true,
-		`uncommon_address@test.museum`: true,
-		`local@sld.UPPER`:              true,
-		`@missing.org`:                 false,
-		`missing@.com`:                 false,
-		`missing@qq.`:                  false,
-		`wrong-ip@127.1.1.1.26`:        false,
-	}
-	for e, r := range emails {
-		b := IsEmail(e)
-		if b != r {
-			t.Errorf("IsEmail:\n Expect => %v\n Got => %v\n", r, b)
-		}
-	}
-}
-
-func TestIsUrl(t *testing.T) {
-	urls := map[string]bool{
-		"http://www.example.com":                     true,
-		"http://example.com":                         true,
-		"http://example.com?user=test&password=test": true,
-		"http://example.com?user=test#login":         true,
-		"ftp://example.com":                          true,
-		"https://example.com":                        true,
-		"htp://example.com":                          false,
-		"http//example.com":                          false,
-		"http://example":                             true,
-	}
-	for u, r := range urls {
-		b := IsUrl(u)
-		if b != r {
-			t.Errorf("IsUrl:\n Expect => %v\n Got => %v\n", r, b)
-		}
-	}
-}
-
-func BenchmarkIsEmail(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsEmail("test@example.com")
-	}
-}
-
-func BenchmarkIsUrl(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsEmail("http://example.com")
-	}
-}

+ 0 - 99
vendor/github.com/Unknwon/com/slice_test.go

@@ -1,99 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"fmt"
-	"testing"
-
-	. "github.com/smartystreets/goconvey/convey"
-)
-
-func TestAppendStr(t *testing.T) {
-	Convey("Append a string to a slice with no duplicates", t, func() {
-		s := []string{"a"}
-
-		Convey("Append a string that does not exist in slice", func() {
-			s = AppendStr(s, "b")
-			So(len(s), ShouldEqual, 2)
-		})
-
-		Convey("Append a string that does exist in slice", func() {
-			s = AppendStr(s, "b")
-			So(len(s), ShouldEqual, 2)
-		})
-	})
-}
-
-func TestCompareSliceStr(t *testing.T) {
-	Convey("Compares two 'string' type slices with elements and order", t, func() {
-		Convey("Compare two slices that do have same elements and order", func() {
-			So(CompareSliceStr(
-				[]string{"1", "2", "3"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-
-		Convey("Compare two slices that do have same elements but does not have same order", func() {
-			So(!CompareSliceStr(
-				[]string{"2", "1", "3"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-
-		Convey("Compare two slices that have different number of elements", func() {
-			So(!CompareSliceStr(
-				[]string{"2", "1"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-	})
-}
-
-func TestCompareSliceStrU(t *testing.T) {
-	Convey("Compare two 'string' type slices with elements and ignore the order", t, func() {
-		Convey("Compare two slices that do have same elements and order", func() {
-			So(CompareSliceStrU(
-				[]string{"1", "2", "3"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-
-		Convey("Compare two slices that do have same elements but does not have same order", func() {
-			So(CompareSliceStrU(
-				[]string{"2", "1", "3"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-
-		Convey("Compare two slices that have different number of elements", func() {
-			So(!CompareSliceStrU(
-				[]string{"2", "1"}, []string{"1", "2", "3"}), ShouldBeTrue)
-		})
-	})
-}
-
-func BenchmarkAppendStr(b *testing.B) {
-	s := []string{"a"}
-	for i := 0; i < b.N; i++ {
-		s = AppendStr(s, fmt.Sprint(b.N%3))
-	}
-}
-
-func BenchmarkCompareSliceStr(b *testing.B) {
-	s1 := []string{"1", "2", "3"}
-	s2 := []string{"1", "2", "3"}
-	for i := 0; i < b.N; i++ {
-		CompareSliceStr(s1, s2)
-	}
-}
-
-func BenchmarkCompareSliceStrU(b *testing.B) {
-	s1 := []string{"1", "4", "2", "3"}
-	s2 := []string{"1", "2", "3", "4"}
-	for i := 0; i < b.N; i++ {
-		CompareSliceStrU(s1, s2)
-	}
-}

+ 134 - 21
vendor/github.com/Unknwon/com/string.go

@@ -15,53 +15,66 @@
 package com
 package com
 
 
 import (
 import (
+	"bytes"
 	"crypto/aes"
 	"crypto/aes"
 	"crypto/cipher"
 	"crypto/cipher"
 	"crypto/rand"
 	"crypto/rand"
-	"encoding/base64"
 	"errors"
 	"errors"
-	"io"
 	r "math/rand"
 	r "math/rand"
 	"strconv"
 	"strconv"
 	"strings"
 	"strings"
 	"time"
 	"time"
+	"unicode"
+	"unicode/utf8"
 )
 )
 
 
-// AESEncrypt encrypts text and given key with AES.
-func AESEncrypt(key, text []byte) ([]byte, error) {
+// AESGCMEncrypt encrypts plaintext with the given key using AES in GCM mode.
+func AESGCMEncrypt(key, plaintext []byte) ([]byte, error) {
 	block, err := aes.NewCipher(key)
 	block, err := aes.NewCipher(key)
 	if err != nil {
 	if err != nil {
 		return nil, err
 		return nil, err
 	}
 	}
-	b := base64.StdEncoding.EncodeToString(text)
-	ciphertext := make([]byte, aes.BlockSize+len(b))
-	iv := ciphertext[:aes.BlockSize]
-	if _, err := io.ReadFull(rand.Reader, iv); err != nil {
+
+	gcm, err := cipher.NewGCM(block)
+	if err != nil {
+		return nil, err
+	}
+
+	nonce := make([]byte, gcm.NonceSize())
+	if _, err := rand.Read(nonce); err != nil {
 		return nil, err
 		return nil, err
 	}
 	}
-	cfb := cipher.NewCFBEncrypter(block, iv)
-	cfb.XORKeyStream(ciphertext[aes.BlockSize:], []byte(b))
-	return ciphertext, nil
+
+	ciphertext := gcm.Seal(nil, nonce, plaintext, nil)
+	return append(nonce, ciphertext...), nil
 }
 }
 
 
-// AESDecrypt decrypts text and given key with AES.
-func AESDecrypt(key, text []byte) ([]byte, error) {
+// AESGCMDecrypt decrypts ciphertext with the given key using AES in GCM mode.
+func AESGCMDecrypt(key, ciphertext []byte) ([]byte, error) {
 	block, err := aes.NewCipher(key)
 	block, err := aes.NewCipher(key)
 	if err != nil {
 	if err != nil {
 		return nil, err
 		return nil, err
 	}
 	}
-	if len(text) < aes.BlockSize {
-		return nil, errors.New("ciphertext too short")
+
+	gcm, err := cipher.NewGCM(block)
+	if err != nil {
+		return nil, err
 	}
 	}
-	iv := text[:aes.BlockSize]
-	text = text[aes.BlockSize:]
-	cfb := cipher.NewCFBDecrypter(block, iv)
-	cfb.XORKeyStream(text, text)
-	data, err := base64.StdEncoding.DecodeString(string(text))
+
+	size := gcm.NonceSize()
+	if len(ciphertext)-size <= 0 {
+		return nil, errors.New("Ciphertext is empty")
+	}
+
+	nonce := ciphertext[:size]
+	ciphertext = ciphertext[size:]
+
+	plainText, err := gcm.Open(nil, nonce, ciphertext, nil)
 	if err != nil {
 	if err != nil {
 		return nil, err
 		return nil, err
 	}
 	}
-	return data, nil
+
+	return plainText, nil
 }
 }
 
 
 // IsLetter returns true if the 'l' is an English letter.
 // IsLetter returns true if the 'l' is an English letter.
@@ -138,3 +151,103 @@ func RandomCreateBytes(n int, alphabets ...byte) []byte {
 	}
 	}
 	return bytes
 	return bytes
 }
 }
+
+// ToSnakeCase can convert all upper case characters in a string to
+// underscore format.
+//
+// Some samples.
+//     "FirstName"  => "first_name"
+//     "HTTPServer" => "http_server"
+//     "NoHTTPS"    => "no_https"
+//     "GO_PATH"    => "go_path"
+//     "GO PATH"    => "go_path"      // space is converted to underscore.
+//     "GO-PATH"    => "go_path"      // hyphen is converted to underscore.
+//
+// From https://github.com/huandu/xstrings
+func ToSnakeCase(str string) string {
+	if len(str) == 0 {
+		return ""
+	}
+
+	buf := &bytes.Buffer{}
+	var prev, r0, r1 rune
+	var size int
+
+	r0 = '_'
+
+	for len(str) > 0 {
+		prev = r0
+		r0, size = utf8.DecodeRuneInString(str)
+		str = str[size:]
+
+		switch {
+		case r0 == utf8.RuneError:
+			buf.WriteByte(byte(str[0]))
+
+		case unicode.IsUpper(r0):
+			if prev != '_' {
+				buf.WriteRune('_')
+			}
+
+			buf.WriteRune(unicode.ToLower(r0))
+
+			if len(str) == 0 {
+				break
+			}
+
+			r0, size = utf8.DecodeRuneInString(str)
+			str = str[size:]
+
+			if !unicode.IsUpper(r0) {
+				buf.WriteRune(r0)
+				break
+			}
+
+			// find next non-upper-case character and insert `_` properly.
+			// it's designed to convert `HTTPServer` to `http_server`.
+			// if there are more than 2 adjacent upper case characters in a word,
+			// treat them as an abbreviation plus a normal word.
+			for len(str) > 0 {
+				r1 = r0
+				r0, size = utf8.DecodeRuneInString(str)
+				str = str[size:]
+
+				if r0 == utf8.RuneError {
+					buf.WriteRune(unicode.ToLower(r1))
+					buf.WriteByte(byte(str[0]))
+					break
+				}
+
+				if !unicode.IsUpper(r0) {
+					if r0 == '_' || r0 == ' ' || r0 == '-' {
+						r0 = '_'
+
+						buf.WriteRune(unicode.ToLower(r1))
+					} else {
+						buf.WriteRune('_')
+						buf.WriteRune(unicode.ToLower(r1))
+						buf.WriteRune(r0)
+					}
+
+					break
+				}
+
+				buf.WriteRune(unicode.ToLower(r1))
+			}
+
+			if len(str) == 0 || r0 == '_' {
+				buf.WriteRune(unicode.ToLower(r0))
+				break
+			}
+
+		default:
+			if r0 == ' ' || r0 == '-' {
+				r0 = '_'
+			}
+
+			buf.WriteRune(r0)
+		}
+	}
+
+	return buf.String()
+}

+ 0 - 82
vendor/github.com/Unknwon/com/string_test.go

@@ -1,82 +0,0 @@
-// Copyright 2013 com authors
-//
-// Licensed under the Apache License, Version 2.0 (the "License"): you may
-// not use this file except in compliance with the License. You may obtain
-// a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
-// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
-// License for the specific language governing permissions and limitations
-// under the License.
-
-package com
-
-import (
-	"testing"
-)
-
-func TestIsLetter(t *testing.T) {
-	if IsLetter('1') {
-		t.Errorf("IsLetter:\n Expect => %v\n Got => %v\n", false, true)
-	}
-
-	if IsLetter('[') {
-		t.Errorf("IsLetter:\n Expect => %v\n Got => %v\n", false, true)
-	}
-
-	if !IsLetter('a') {
-		t.Errorf("IsLetter:\n Expect => %v\n Got => %v\n", true, false)
-	}
-
-	if !IsLetter('Z') {
-		t.Errorf("IsLetter:\n Expect => %v\n Got => %v\n", true, false)
-	}
-}
-
-func TestExpand(t *testing.T) {
-	match := map[string]string{
-		"domain":    "gowalker.org",
-		"subdomain": "github.com",
-	}
-	s := "http://{domain}/{subdomain}/{0}/{1}"
-	sR := "http://gowalker.org/github.com/Unknwon/gowalker"
-	if Expand(s, match, "Unknwon", "gowalker") != sR {
-		t.Errorf("Expand:\n Expect => %s\n Got => %s\n", sR, s)
-	}
-}
-
-func TestReverse(t *testing.T) {
-	if Reverse("abcdefg") != "gfedcba" {
-		t.Errorf("Reverse:\n Except => %s\n Got =>%s\n", "gfedcba", Reverse("abcdefg"))
-	}
-	if Reverse("上善若水厚德载物") != "物载德厚水若善上" {
-		t.Errorf("Reverse:\n Except => %s\n Got =>%s\n", "物载德厚水若善上", Reverse("上善若水厚德载物"))
-	}
-}
-
-func BenchmarkIsLetter(b *testing.B) {
-	for i := 0; i < b.N; i++ {
-		IsLetter('a')
-	}
-}
-
-func BenchmarkExpand(b *testing.B) {
-	match := map[string]string{
-		"domain":    "gowalker.org",
-		"subdomain": "github.com",
-	}
-	s := "http://{domain}/{subdomain}/{0}/{1}"
-	for i := 0; i < b.N; i++ {
-		Expand(s, match, "Unknwon", "gowalker")
-	}
-}
-
-func BenchmarkReverse(b *testing.B) {
-	s := "abscef中文"
-	for i := 0; i < b.N; i++ {
-		Reverse(s)
-	}
-}

+ 0 - 14
vendor/github.com/go-macaron/binding/.travis.yml

@@ -1,14 +0,0 @@
-sudo: false
-language: go
-
-go:
-  - 1.3
-  - 1.4
-  - 1.5
-  - tip
-
-script: go test -v -cover -race
-
-notifications:
-  email:
-    - u@gogs.io

+ 28 - 22
vendor/github.com/go-macaron/binding/binding.go

@@ -32,7 +32,7 @@ import (
 	"gopkg.in/macaron.v1"
 	"gopkg.in/macaron.v1"
 )
 )
 
 
-const _VERSION = "0.2.0"
+const _VERSION = "0.3.2"
 
 
 func Version() string {
 func Version() string {
 	return _VERSION
 	return _VERSION
@@ -145,7 +145,7 @@ func Form(formStruct interface{}, ifacePtr ...interface{}) macaron.Handler {
 		if parseErr != nil {
 		if parseErr != nil {
 			errors.Add([]string{}, ERR_DESERIALIZATION, parseErr.Error())
 			errors.Add([]string{}, ERR_DESERIALIZATION, parseErr.Error())
 		}
 		}
-		mapForm(formStruct, ctx.Req.Form, nil, errors)
+		errors = mapForm(formStruct, ctx.Req.Form, nil, errors)
 		validateAndMap(formStruct, ctx, errors, ifacePtr...)
 		validateAndMap(formStruct, ctx, errors, ifacePtr...)
 	}
 	}
 }
 }
@@ -185,7 +185,7 @@ func MultipartForm(formStruct interface{}, ifacePtr ...interface{}) macaron.Hand
 				ctx.Req.MultipartForm = form
 				ctx.Req.MultipartForm = form
 			}
 			}
 		}
 		}
-		mapForm(formStruct, ctx.Req.MultipartForm.Value, ctx.Req.MultipartForm.File, errors)
+		errors = mapForm(formStruct, ctx.Req.MultipartForm.Value, ctx.Req.MultipartForm.File, errors)
 		validateAndMap(formStruct, ctx, errors, ifacePtr...)
 		validateAndMap(formStruct, ctx, errors, ifacePtr...)
 	}
 	}
 }
 }
@@ -243,10 +243,10 @@ func Validate(obj interface{}) macaron.Handler {
 }
 }
 
 
 var (
 var (
-	alphaDashPattern    = regexp.MustCompile("[^\\d\\w-_]")
-	alphaDashDotPattern = regexp.MustCompile("[^\\d\\w-_\\.]")
-	emailPattern        = regexp.MustCompile("[\\w!#$%&'*+/=?^_`{|}~-]+(?:\\.[\\w!#$%&'*+/=?^_`{|}~-]+)*@(?:[\\w](?:[\\w-]*[\\w])?\\.)+[a-zA-Z0-9](?:[\\w-]*[\\w])?")
-	urlPattern          = regexp.MustCompile(`(http|https):\/\/[\w\-_]+(\.[\w\-_]+)+([\w\-\.,@?^=%&amp;:/~\+#]*[\w\-\@?^=%&amp;/~\+#])?`)
+	AlphaDashPattern    = regexp.MustCompile("[^\\d\\w-_]")
+	AlphaDashDotPattern = regexp.MustCompile("[^\\d\\w-_\\.]")
+	EmailPattern        = regexp.MustCompile("[\\w!#$%&'*+/=?^_`{|}~-]+(?:\\.[\\w!#$%&'*+/=?^_`{|}~-]+)*@(?:[\\w](?:[\\w-]*[\\w])?\\.)+[a-zA-Z0-9](?:[\\w-]*[\\w])?")
+	URLPattern          = regexp.MustCompile(`(http|https):\/\/(?:\\S+(?::\\S*)?@)?[\w\-_]+(\.[\w\-_]+)*([\w\-\.,@?^=%&amp;:/~\+#]*[\w\-\@?^=%&amp;/~\+#])?`)
 )
 )
 
 
 type (
 type (
@@ -255,7 +255,7 @@ type (
 		// IsMatch checks if rule matches.
 		// IsMatch checks if rule matches.
 		IsMatch func(string) bool
 		IsMatch func(string) bool
 		// IsValid applies validation rule to condition.
 		// IsValid applies validation rule to condition.
-		IsValid func(Errors, string, interface{}) bool
+		IsValid func(Errors, string, interface{}) (bool, Errors)
 	}
 	}
 	// RuleMapper represents a validation rule mapper,
 	// RuleMapper represents a validation rule mapper,
 	// it allwos users to add custom validation rules.
 	// it allwos users to add custom validation rules.
@@ -361,12 +361,12 @@ VALIDATE_RULES:
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
 		case rule == "AlphaDash":
 		case rule == "AlphaDash":
-			if alphaDashPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
+			if AlphaDashPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
 				errors.Add([]string{field.Name}, ERR_ALPHA_DASH, "AlphaDash")
 				errors.Add([]string{field.Name}, ERR_ALPHA_DASH, "AlphaDash")
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
 		case rule == "AlphaDashDot":
 		case rule == "AlphaDashDot":
-			if alphaDashDotPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
+			if AlphaDashDotPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
 				errors.Add([]string{field.Name}, ERR_ALPHA_DASH_DOT, "AlphaDashDot")
 				errors.Add([]string{field.Name}, ERR_ALPHA_DASH_DOT, "AlphaDashDot")
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
@@ -414,7 +414,7 @@ VALIDATE_RULES:
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
 		case rule == "Email":
 		case rule == "Email":
-			if !emailPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
+			if !EmailPattern.MatchString(fmt.Sprintf("%v", fieldValue)) {
 				errors.Add([]string{field.Name}, ERR_EMAIL, "Email")
 				errors.Add([]string{field.Name}, ERR_EMAIL, "Email")
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
@@ -422,7 +422,7 @@ VALIDATE_RULES:
 			str := fmt.Sprintf("%v", fieldValue)
 			str := fmt.Sprintf("%v", fieldValue)
 			if len(str) == 0 {
 			if len(str) == 0 {
 				continue
 				continue
-			} else if !urlPattern.MatchString(str) {
+			} else if !URLPattern.MatchString(str) {
 				errors.Add([]string{field.Name}, ERR_URL, "Url")
 				errors.Add([]string{field.Name}, ERR_URL, "Url")
 				break VALIDATE_RULES
 				break VALIDATE_RULES
 			}
 			}
@@ -449,7 +449,7 @@ VALIDATE_RULES:
 		case strings.HasPrefix(rule, "Default("):
 		case strings.HasPrefix(rule, "Default("):
 			if reflect.DeepEqual(zero, fieldValue) {
 			if reflect.DeepEqual(zero, fieldValue) {
 				if fieldVal.CanAddr() {
 				if fieldVal.CanAddr() {
-					setWithProperType(field.Type.Kind(), rule[8:len(rule)-1], fieldVal, field.Tag.Get("form"), errors)
+					errors = setWithProperType(field.Type.Kind(), rule[8:len(rule)-1], fieldVal, field.Tag.Get("form"), errors)
 				} else {
 				} else {
 					errors.Add([]string{field.Name}, ERR_EXCLUDE, "Default")
 					errors.Add([]string{field.Name}, ERR_EXCLUDE, "Default")
 					break VALIDATE_RULES
 					break VALIDATE_RULES
@@ -457,9 +457,13 @@ VALIDATE_RULES:
 			}
 			}
 		default:
 		default:
 			// Apply custom validation rules.
 			// Apply custom validation rules.
+			var isValid bool
 			for i := range ruleMapper {
 			for i := range ruleMapper {
-				if ruleMapper[i].IsMatch(rule) && !ruleMapper[i].IsValid(errors, field.Name, fieldValue) {
-					break VALIDATE_RULES
+				if ruleMapper[i].IsMatch(rule) {
+					isValid, errors = ruleMapper[i].IsValid(errors, field.Name, fieldValue)
+					if !isValid {
+						break VALIDATE_RULES
+					}
 				}
 				}
 			}
 			}
 		}
 		}
@@ -493,7 +497,7 @@ func SetNameMapper(nm NameMapper) {
 
 
 // Takes values from the form data and puts them into a struct
 // Takes values from the form data and puts them into a struct
 func mapForm(formStruct reflect.Value, form map[string][]string,
 func mapForm(formStruct reflect.Value, form map[string][]string,
-	formfile map[string][]*multipart.FileHeader, errors Errors) {
+	formfile map[string][]*multipart.FileHeader, errors Errors) Errors {
 
 
 	if formStruct.Kind() == reflect.Ptr {
 	if formStruct.Kind() == reflect.Ptr {
 		formStruct = formStruct.Elem()
 		formStruct = formStruct.Elem()
@@ -506,12 +510,12 @@ func mapForm(formStruct reflect.Value, form map[string][]string,
 
 
 		if typeField.Type.Kind() == reflect.Ptr && typeField.Anonymous {
 		if typeField.Type.Kind() == reflect.Ptr && typeField.Anonymous {
 			structField.Set(reflect.New(typeField.Type.Elem()))
 			structField.Set(reflect.New(typeField.Type.Elem()))
-			mapForm(structField.Elem(), form, formfile, errors)
+			errors = mapForm(structField.Elem(), form, formfile, errors)
 			if reflect.DeepEqual(structField.Elem().Interface(), reflect.Zero(structField.Elem().Type()).Interface()) {
 			if reflect.DeepEqual(structField.Elem().Interface(), reflect.Zero(structField.Elem().Type()).Interface()) {
 				structField.Set(reflect.Zero(structField.Type()))
 				structField.Set(reflect.Zero(structField.Type()))
 			}
 			}
 		} else if typeField.Type.Kind() == reflect.Struct {
 		} else if typeField.Type.Kind() == reflect.Struct {
-			mapForm(structField, form, formfile, errors)
+			errors = mapForm(structField, form, formfile, errors)
 		}
 		}
 
 
 		inputFieldName := parseFormName(typeField.Name, typeField.Tag.Get("form"))
 		inputFieldName := parseFormName(typeField.Name, typeField.Tag.Get("form"))
@@ -526,11 +530,11 @@ func mapForm(formStruct reflect.Value, form map[string][]string,
 				sliceOf := structField.Type().Elem().Kind()
 				sliceOf := structField.Type().Elem().Kind()
 				slice := reflect.MakeSlice(structField.Type(), numElems, numElems)
 				slice := reflect.MakeSlice(structField.Type(), numElems, numElems)
 				for i := 0; i < numElems; i++ {
 				for i := 0; i < numElems; i++ {
-					setWithProperType(sliceOf, inputValue[i], slice.Index(i), inputFieldName, errors)
+					errors = setWithProperType(sliceOf, inputValue[i], slice.Index(i), inputFieldName, errors)
 				}
 				}
 				formStruct.Field(i).Set(slice)
 				formStruct.Field(i).Set(slice)
 			} else {
 			} else {
-				setWithProperType(typeField.Type.Kind(), inputValue[0], structField, inputFieldName, errors)
+				errors = setWithProperType(typeField.Type.Kind(), inputValue[0], structField, inputFieldName, errors)
 			}
 			}
 			continue
 			continue
 		}
 		}
@@ -551,13 +555,14 @@ func mapForm(formStruct reflect.Value, form map[string][]string,
 			structField.Set(reflect.ValueOf(inputFile[0]))
 			structField.Set(reflect.ValueOf(inputFile[0]))
 		}
 		}
 	}
 	}
+	return errors
 }
 }
 
 
 // This sets the value in a struct of an indeterminate type to the
 // This sets the value in a struct of an indeterminate type to the
 // matching value from the request (via Form middleware) in the
 // matching value from the request (via Form middleware) in the
 // same type, so that not all deserialized values have to be strings.
 // same type, so that not all deserialized values have to be strings.
 // Supported types are string, int, float, and bool.
 // Supported types are string, int, float, and bool.
-func setWithProperType(valueKind reflect.Kind, val string, structField reflect.Value, nameInTag string, errors Errors) {
+func setWithProperType(valueKind reflect.Kind, val string, structField reflect.Value, nameInTag string, errors Errors) Errors {
 	switch valueKind {
 	switch valueKind {
 	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
 	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
 		if val == "" {
 		if val == "" {
@@ -582,7 +587,7 @@ func setWithProperType(valueKind reflect.Kind, val string, structField reflect.V
 	case reflect.Bool:
 	case reflect.Bool:
 		if val == "on" {
 		if val == "on" {
 			structField.SetBool(true)
 			structField.SetBool(true)
-			return
+			break
 		}
 		}
 
 
 		if val == "" {
 		if val == "" {
@@ -617,6 +622,7 @@ func setWithProperType(valueKind reflect.Kind, val string, structField reflect.V
 	case reflect.String:
 	case reflect.String:
 		structField.SetString(val)
 		structField.SetString(val)
 	}
 	}
+	return errors
 }
 }
 
 
 // Don't pass in pointers to bind to. Can lead to bugs.
 // Don't pass in pointers to bind to. Can lead to bugs.

+ 0 - 14
vendor/github.com/go-macaron/inject/.travis.yml

@@ -1,14 +0,0 @@
-sudo: false
-language: go
-
-go:
-  - 1.3
-  - 1.4
-  - 1.5
-  - tip
-
-script: go test -v -cover -race
-
-notifications:
-  email:
-    - u@gogs.io

+ 68 - 8
vendor/github.com/go-macaron/inject/inject.go

@@ -50,6 +50,34 @@ type Invoker interface {
 	Invoke(interface{}) ([]reflect.Value, error)
 	Invoke(interface{}) ([]reflect.Value, error)
 }
 }
 
 
+// FastInvoker represents an interface in order to avoid the calling function via reflection.
+//
+// example:
+//	type handlerFuncHandler func(http.ResponseWriter, *http.Request) error
+//	func (f handlerFuncHandler)Invoke([]interface{}) ([]reflect.Value, error){
+//		ret := f(p[0].(http.ResponseWriter), p[1].(*http.Request))
+//		return []reflect.Value{reflect.ValueOf(ret)}, nil
+//	}
+//
+//	type funcHandler func(int, string)
+//	func (f funcHandler)Invoke([]interface{}) ([]reflect.Value, error){
+//		f(p[0].(int), p[1].(string))
+//		return nil, nil
+//	}
+type FastInvoker interface {
+	// Invoke attempts to call the ordinary functions. If f is a function
+	// with the appropriate signature, f.Invoke([]interface{}) is a Call that calls f.
+	// Returns a slice of reflect.Value representing the returned values of the function.
+	// Returns an error if the injection fails.
+	Invoke([]interface{}) ([]reflect.Value, error)
+}
+
+// IsFastInvoker check interface is FastInvoker
+func IsFastInvoker(h interface{}) bool {
+	_, ok := h.(FastInvoker)
+	return ok
+}
+
 // TypeMapper represents an interface for mapping interface{} values based on type.
 // TypeMapper represents an interface for mapping interface{} values based on type.
 type TypeMapper interface {
 type TypeMapper interface {
 	// Maps the interface{} value based on its immediate type from reflect.TypeOf.
 	// Maps the interface{} value based on its immediate type from reflect.TypeOf.
@@ -102,18 +130,50 @@ func New() Injector {
 // It panics if f is not a function
 // It panics if f is not a function
 func (inj *injector) Invoke(f interface{}) ([]reflect.Value, error) {
 func (inj *injector) Invoke(f interface{}) ([]reflect.Value, error) {
 	t := reflect.TypeOf(f)
 	t := reflect.TypeOf(f)
+	switch v := f.(type) {
+	case FastInvoker:
+		return inj.fastInvoke(v, t, t.NumIn())
+	default:
+		return inj.callInvoke(f, t, t.NumIn())
+	}
+}
 
 
-	var in = make([]reflect.Value, t.NumIn()) //Panic if t is not kind of Func
-	for i := 0; i < t.NumIn(); i++ {
-		argType := t.In(i)
-		val := inj.GetVal(argType)
-		if !val.IsValid() {
-			return nil, fmt.Errorf("Value not found for type %v", argType)
-		}
+func (inj *injector) fastInvoke(f FastInvoker, t reflect.Type, numIn int) ([]reflect.Value, error) {
+	var in []interface{}
+	if numIn > 0 {
+		in = make([]interface{}, numIn) // Panic if t is not kind of Func
+		var argType reflect.Type
+		var val reflect.Value
+		for i := 0; i < numIn; i++ {
+			argType = t.In(i)
+			val = inj.GetVal(argType)
+			if !val.IsValid() {
+				return nil, fmt.Errorf("Value not found for type %v", argType)
+			}
 
 
-		in[i] = val
+			in[i] = val.Interface()
+		}
 	}
 	}
+	return f.Invoke(in)
+}
 
 
+// callInvoke reflect.Value.Call
+func (inj *injector) callInvoke(f interface{}, t reflect.Type, numIn int) ([]reflect.Value, error) {
+	var in []reflect.Value
+	if numIn > 0 {
+		in = make([]reflect.Value, numIn)
+		var argType reflect.Type
+		var val reflect.Value
+		for i := 0; i < numIn; i++ {
+			argType = t.In(i)
+			val = inj.GetVal(argType)
+			if !val.IsValid() {
+				return nil, fmt.Errorf("Value not found for type %v", argType)
+			}
+
+			in[i] = val
+		}
+	}
 	return reflect.ValueOf(f).Call(in), nil
 	return reflect.ValueOf(f).Call(in), nil
 }
 }
 
 

+ 0 - 2
vendor/github.com/go-macaron/session/.gitignore

@@ -1,2 +0,0 @@
-ledis/tmp.db
-nodb/tmp.db

+ 0 - 14
vendor/github.com/go-macaron/session/.travis.yml

@@ -1,14 +0,0 @@
-sudo: false
-language: go
-
-go:
-  - 1.3
-  - 1.4
-  - 1.5
-  - tip
-
-script: go test -v -cover -race
-
-notifications:
-  email:
-    - u@gogs.io

+ 2 - 2
vendor/github.com/go-macaron/session/README.md

@@ -1,4 +1,4 @@
-# session [![Build Status](https://travis-ci.org/go-macaron/session.svg?branch=master)](https://travis-ci.org/go-macaron/session) [![](http://gocover.io/_badge/github.com/go-macaron/session)](http://gocover.io/github.com/go-macaron/session)
+# session [![Build Status](https://travis-ci.org/go-macaron/session.svg?branch=master)](https://travis-ci.org/go-macaron/session)
 
 
 Middleware session provides session management for [Macaron](https://github.com/go-macaron/macaron). It can use many session providers, including memory, file, Redis, Memcache, PostgreSQL, MySQL, Couchbase, Ledis and Nodb.
 Middleware session provides session management for [Macaron](https://github.com/go-macaron/macaron). It can use many session providers, including memory, file, Redis, Memcache, PostgreSQL, MySQL, Couchbase, Ledis and Nodb.
 
 
@@ -9,7 +9,7 @@ Middleware session provides session management for [Macaron](https://github.com/
 ## Getting Help
 ## Getting Help
 
 
 - [API Reference](https://gowalker.org/github.com/go-macaron/session)
 - [API Reference](https://gowalker.org/github.com/go-macaron/session)
-- [Documentation](http://go-macaron.com/docs/middlewares/session)
+- [Documentation](https://go-macaron.com/docs/middlewares/session)
 
 
 ## Credits
 ## Credits
 
 

+ 6 - 6
vendor/github.com/go-macaron/session/file.go

@@ -86,7 +86,7 @@ func (s *FileStore) Release() error {
 		return err
 		return err
 	}
 	}
 
 
-	return ioutil.WriteFile(s.p.filepath(s.sid), data, os.ModePerm)
+	return ioutil.WriteFile(s.p.filepath(s.sid), data, 0600)
 }
 }
 
 
 // Flush deletes all session data.
 // Flush deletes all session data.
@@ -121,7 +121,7 @@ func (p *FileProvider) filepath(sid string) string {
 // Read returns raw session store by session ID.
 // Read returns raw session store by session ID.
 func (p *FileProvider) Read(sid string) (_ RawStore, err error) {
 func (p *FileProvider) Read(sid string) (_ RawStore, err error) {
 	filename := p.filepath(sid)
 	filename := p.filepath(sid)
-	if err = os.MkdirAll(path.Dir(filename), os.ModePerm); err != nil {
+	if err = os.MkdirAll(path.Dir(filename), 0700); err != nil {
 		return nil, err
 		return nil, err
 	}
 	}
 	p.lock.RLock()
 	p.lock.RLock()
@@ -129,7 +129,7 @@ func (p *FileProvider) Read(sid string) (_ RawStore, err error) {
 
 
 	var f *os.File
 	var f *os.File
 	if com.IsFile(filename) {
 	if com.IsFile(filename) {
-		f, err = os.OpenFile(filename, os.O_RDWR, os.ModePerm)
+		f, err = os.OpenFile(filename, os.O_RDONLY, 0600)
 	} else {
 	} else {
 		f, err = os.Create(filename)
 		f, err = os.Create(filename)
 	}
 	}
@@ -187,15 +187,15 @@ func (p *FileProvider) regenerate(oldsid, sid string) (err error) {
 		if err != nil {
 		if err != nil {
 			return err
 			return err
 		}
 		}
-		if err = os.MkdirAll(path.Dir(oldname), os.ModePerm); err != nil {
+		if err = os.MkdirAll(path.Dir(oldname), 0700); err != nil {
 			return err
 			return err
 		}
 		}
-		if err = ioutil.WriteFile(oldname, data, os.ModePerm); err != nil {
+		if err = ioutil.WriteFile(oldname, data, 0600); err != nil {
 			return err
 			return err
 		}
 		}
 	}
 	}
 
 
-	if err = os.MkdirAll(path.Dir(filename), os.ModePerm); err != nil {
+	if err = os.MkdirAll(path.Dir(filename), 0700); err != nil {
 		return err
 		return err
 	}
 	}
 	if err = os.Rename(oldname, filename); err != nil {
 	if err = os.Rename(oldname, filename); err != nil {

+ 27 - 0
vendor/golang.org/x/crypto/LICENSE

@@ -0,0 +1,27 @@
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+   * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+   * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+   * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

+ 22 - 0
vendor/golang.org/x/crypto/PATENTS

@@ -0,0 +1,22 @@
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go.  This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation.  If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.

+ 77 - 0
vendor/golang.org/x/crypto/pbkdf2/pbkdf2.go

@@ -0,0 +1,77 @@
+// Copyright 2012 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+/*
+Package pbkdf2 implements the key derivation function PBKDF2 as defined in RFC
+2898 / PKCS #5 v2.0.
+
+A key derivation function is useful when encrypting data based on a password
+or any other not-fully-random data. It uses a pseudorandom function to derive
+a secure encryption key based on the password.
+
+While v2.0 of the standard defines only one pseudorandom function to use,
+HMAC-SHA1, the drafted v2.1 specification allows use of all five FIPS Approved
+Hash Functions SHA-1, SHA-224, SHA-256, SHA-384 and SHA-512 for HMAC. To
+choose, you can pass the `New` functions from the different SHA packages to
+pbkdf2.Key.
+*/
+package pbkdf2 // import "golang.org/x/crypto/pbkdf2"
+
+import (
+	"crypto/hmac"
+	"hash"
+)
+
+// Key derives a key from the password, salt and iteration count, returning a
+// []byte of length keylen that can be used as cryptographic key. The key is
+// derived based on the method described as PBKDF2 with the HMAC variant using
+// the supplied hash function.
+//
+// For example, to use a HMAC-SHA-1 based PBKDF2 key derivation function, you
+// can get a derived key for e.g. AES-256 (which needs a 32-byte key) by
+// doing:
+//
+// 	dk := pbkdf2.Key([]byte("some password"), salt, 4096, 32, sha1.New)
+//
+// Remember to get a good random salt. At least 8 bytes is recommended by the
+// RFC.
+//
+// Using a higher iteration count will increase the cost of an exhaustive
+// search but will also make derivation proportionally slower.
+func Key(password, salt []byte, iter, keyLen int, h func() hash.Hash) []byte {
+	prf := hmac.New(h, password)
+	hashLen := prf.Size()
+	numBlocks := (keyLen + hashLen - 1) / hashLen
+
+	var buf [4]byte
+	dk := make([]byte, 0, numBlocks*hashLen)
+	U := make([]byte, hashLen)
+	for block := 1; block <= numBlocks; block++ {
+		// N.B.: || means concatenation, ^ means XOR
+		// for each block T_i = U_1 ^ U_2 ^ ... ^ U_iter
+		// U_1 = PRF(password, salt || uint(i))
+		prf.Reset()
+		prf.Write(salt)
+		buf[0] = byte(block >> 24)
+		buf[1] = byte(block >> 16)
+		buf[2] = byte(block >> 8)
+		buf[3] = byte(block)
+		prf.Write(buf[:4])
+		dk = prf.Sum(dk)
+		T := dk[len(dk)-hashLen:]
+		copy(U, T)
+
+		// U_n = PRF(password, U_(n-1))
+		for n := 2; n <= iter; n++ {
+			prf.Reset()
+			prf.Write(U)
+			U = U[:0]
+			U = prf.Sum(U)
+			for x := range U {
+				T[x] ^= U[x]
+			}
+		}
+	}
+	return dk[:keyLen]
+}

+ 0 - 2
vendor/gopkg.in/macaron.v1/.gitignore

@@ -1,2 +0,0 @@
-macaron.sublime-project
-macaron.sublime-workspace

+ 0 - 13
vendor/gopkg.in/macaron.v1/.travis.yml

@@ -1,13 +0,0 @@
-sudo: false
-language: go
-
-go:
-  - 1.3
-  - 1.4
-  - 1.5
-
-script: go test -v -cover -race
-
-notifications:
-  email:
-    - u@gogs.io

+ 6 - 8
vendor/gopkg.in/macaron.v1/README.md

@@ -1,12 +1,10 @@
-Macaron [![Build Status](https://travis-ci.org/go-macaron/macaron.svg?branch=v1)](https://travis-ci.org/go-macaron/macaron) [![](http://gocover.io/_badge/github.com/go-macaron/macaron)](http://gocover.io/github.com/go-macaron/macaron)
+Macaron [![Build Status](https://travis-ci.org/go-macaron/macaron.svg?branch=v1)](https://travis-ci.org/go-macaron/macaron)
 =======================
 =======================
 
 
 ![Macaron Logo](https://raw.githubusercontent.com/go-macaron/macaron/v1/macaronlogo.png)
 ![Macaron Logo](https://raw.githubusercontent.com/go-macaron/macaron/v1/macaronlogo.png)
 
 
 Package macaron is a high productive and modular web framework in Go.
 Package macaron is a high productive and modular web framework in Go.
 
 
-##### Current version: 0.8.0
-
 ## Getting Started
 ## Getting Started
 
 
 The minimum requirement of Go is **1.3**.
 The minimum requirement of Go is **1.3**.
@@ -70,18 +68,18 @@ There are already many [middlewares](https://github.com/go-macaron) to simplify
 
 
 ## Use Cases
 ## Use Cases
 
 
-- [Gogs](http://gogs.io): A painless self-hosted Git Service
-- [Peach](http://peachdocs.org): A modern web documentation server
+- [Gogs](https://gogs.io): A painless self-hosted Git Service
+- [Peach](https://peachdocs.org): A modern web documentation server
 - [Go Walker](https://gowalker.org): Go online API documentation
 - [Go Walker](https://gowalker.org): Go online API documentation
-- [Switch](http://gopm.io): Gopm registry
+- [Switch](https://gopm.io): Gopm registry
 - [YouGam](http://yougam.com): Online Forum
 - [YouGam](http://yougam.com): Online Forum
 - [Critical Stack Intel](https://intel.criticalstack.com/): A 100% free intel marketplace from Critical Stack, Inc.
 - [Critical Stack Intel](https://intel.criticalstack.com/): A 100% free intel marketplace from Critical Stack, Inc.
 
 
 ## Getting Help
 ## Getting Help
 
 
 - [API Reference](https://gowalker.org/gopkg.in/macaron.v1)
 - [API Reference](https://gowalker.org/gopkg.in/macaron.v1)
-- [Documentation](http://go-macaron.com)
-- [FAQs](http://go-macaron.com/docs/faqs)
+- [Documentation](https://go-macaron.com)
+- [FAQs](https://go-macaron.com/docs/faqs)
 - [![Join the chat at https://gitter.im/Unknwon/macaron](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/go-macaron/macaron?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
 - [![Join the chat at https://gitter.im/Unknwon/macaron](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/go-macaron/macaron?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
 
 
 ## Credits
 ## Credits

+ 33 - 16
vendor/gopkg.in/macaron.v1/context.go

@@ -15,7 +15,7 @@
 package macaron
 package macaron
 
 
 import (
 import (
-	"crypto/md5"
+	"crypto/sha256"
 	"encoding/hex"
 	"encoding/hex"
 	"html/template"
 	"html/template"
 	"io"
 	"io"
@@ -32,8 +32,8 @@ import (
 	"time"
 	"time"
 
 
 	"github.com/Unknwon/com"
 	"github.com/Unknwon/com"
-
 	"github.com/go-macaron/inject"
 	"github.com/go-macaron/inject"
+	"golang.org/x/crypto/pbkdf2"
 )
 )
 
 
 // Locale reprents a localization interface.
 // Locale reprents a localization interface.
@@ -72,6 +72,14 @@ func (r *Request) Body() *RequestBody {
 	return &RequestBody{r.Request.Body}
 	return &RequestBody{r.Request.Body}
 }
 }
 
 
+// ContextInvoker is an inject.FastInvoker wrapper of func(ctx *Context).
+type ContextInvoker func(ctx *Context)
+
+func (invoke ContextInvoker) Invoke(params []interface{}) ([]reflect.Value, error) {
+	invoke(params[0].(*Context))
+	return nil, nil
+}
+
 // Context represents the runtime context of current request of Macaron instance.
 // Context represents the runtime context of current request of Macaron instance.
 // It is the integration of most frequently used middlewares and helper methods.
 // It is the integration of most frequently used middlewares and helper methods.
 type Context struct {
 type Context struct {
@@ -84,7 +92,7 @@ type Context struct {
 	Req    Request
 	Req    Request
 	Resp   ResponseWriter
 	Resp   ResponseWriter
 	params Params
 	params Params
-	Render // Not nil only if you use macaran.Render middleware.
+	Render
 	Locale
 	Locale
 	Data map[string]interface{}
 	Data map[string]interface{}
 }
 }
@@ -145,9 +153,6 @@ func (ctx *Context) RemoteAddr() string {
 }
 }
 
 
 func (ctx *Context) renderHTML(status int, setName, tplName string, data ...interface{}) {
 func (ctx *Context) renderHTML(status int, setName, tplName string, data ...interface{}) {
-	if ctx.Render == nil {
-		panic("renderer middleware hasn't been registered")
-	}
 	if len(data) <= 0 {
 	if len(data) <= 0 {
 		ctx.Render.HTMLSet(status, setName, tplName, ctx.Data)
 		ctx.Render.HTMLSet(status, setName, tplName, ctx.Data)
 	} else if len(data) == 1 {
 	} else if len(data) == 1 {
@@ -159,7 +164,7 @@ func (ctx *Context) renderHTML(status int, setName, tplName string, data ...inte
 
 
 // HTML calls Render.HTML but allows less arguments.
 // HTML calls Render.HTML but allows less arguments.
 func (ctx *Context) HTML(status int, name string, data ...interface{}) {
 func (ctx *Context) HTML(status int, name string, data ...interface{}) {
-	ctx.renderHTML(status, _DEFAULT_TPL_SET_NAME, name, data...)
+	ctx.renderHTML(status, DEFAULT_TPL_SET_NAME, name, data...)
 }
 }
 
 
 // HTML calls Render.HTMLSet but allows less arguments.
 // HTML calls Render.HTMLSet but allows less arguments.
@@ -221,6 +226,12 @@ func (ctx *Context) QueryEscape(name string) string {
 	return template.HTMLEscapeString(ctx.Query(name))
 	return template.HTMLEscapeString(ctx.Query(name))
 }
 }
 
 
+// QueryBool returns query result in bool type.
+func (ctx *Context) QueryBool(name string) bool {
+	v, _ := strconv.ParseBool(ctx.Query(name))
+	return v
+}
+
 // QueryInt returns query result in int type.
 // QueryInt returns query result in int type.
 func (ctx *Context) QueryInt(name string) int {
 func (ctx *Context) QueryInt(name string) int {
 	return com.StrTo(ctx.Query(name)).MustInt()
 	return com.StrTo(ctx.Query(name)).MustInt()
@@ -353,6 +364,13 @@ func (ctx *Context) SetCookie(name string, value string, others ...interface{})
 		}
 		}
 	}
 	}
 
 
+	if len(others) > 5 {
+		if v, ok := others[5].(time.Time); ok {
+			cookie.Expires = v
+			cookie.RawExpires = v.Format(time.UnixDate)
+		}
+	}
+
 	ctx.Resp.Header().Add("Set-Cookie", cookie.String())
 	ctx.Resp.Header().Add("Set-Cookie", cookie.String())
 }
 }
 
 
@@ -401,30 +419,29 @@ func (ctx *Context) GetSecureCookie(key string) (string, bool) {
 
 
 // SetSuperSecureCookie sets given cookie value to response header with secret string.
 // SetSuperSecureCookie sets given cookie value to response header with secret string.
 func (ctx *Context) SetSuperSecureCookie(secret, name, value string, others ...interface{}) {
 func (ctx *Context) SetSuperSecureCookie(secret, name, value string, others ...interface{}) {
-	m := md5.Sum([]byte(secret))
-	secret = hex.EncodeToString(m[:])
-	text, err := com.AESEncrypt([]byte(secret), []byte(value))
+	key := pbkdf2.Key([]byte(secret), []byte(secret), 1000, 16, sha256.New)
+	text, err := com.AESGCMEncrypt(key, []byte(value))
 	if err != nil {
 	if err != nil {
 		panic("error encrypting cookie: " + err.Error())
 		panic("error encrypting cookie: " + err.Error())
 	}
 	}
+
 	ctx.SetCookie(name, hex.EncodeToString(text), others...)
 	ctx.SetCookie(name, hex.EncodeToString(text), others...)
 }
 }
 
 
 // GetSuperSecureCookie returns given cookie value from request header with secret string.
 // GetSuperSecureCookie returns given cookie value from request header with secret string.
-func (ctx *Context) GetSuperSecureCookie(secret, key string) (string, bool) {
-	val := ctx.GetCookie(key)
+func (ctx *Context) GetSuperSecureCookie(secret, name string) (string, bool) {
+	val := ctx.GetCookie(name)
 	if val == "" {
 	if val == "" {
 		return "", false
 		return "", false
 	}
 	}
 
 
-	data, err := hex.DecodeString(val)
+	text, err := hex.DecodeString(val)
 	if err != nil {
 	if err != nil {
 		return "", false
 		return "", false
 	}
 	}
 
 
-	m := md5.Sum([]byte(secret))
-	secret = hex.EncodeToString(m[:])
-	text, err := com.AESDecrypt([]byte(secret), data)
+	key := pbkdf2.Key([]byte(secret), []byte(secret), 1000, 16, sha256.New)
+	text, err = com.AESGCMDecrypt(key, text)
 	return string(text), err == nil
 	return string(text), err == nil
 }
 }
 
 

Some files were not shown because too many files changed in this diff