From 44cf66d7ffc3269cf3ffbe5d09e0751f401b3476 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Torkel=20=C3=96degaard?= Date: Thu, 7 Apr 2016 19:23:20 -0400 Subject: [PATCH 1/2] refactoring(): fixing event things --- package.json | 3 +- public/app/core/time_series2.ts | 2 +- .../features/templating/templateValuesSrv.js | 9 ++- public/app/headers/common.d.ts | 3 +- .../app/headers/es6-promise/es6-promise.d.ts | 73 ------------------- public/app/headers/es6-shim/es6-shim.d.ts | 8 +- public/app/plugins/panel/graph/module.ts | 5 ++ public/test/core/utils/emitter_specs.ts | 22 +++++- 8 files changed, 39 insertions(+), 86 deletions(-) delete mode 100644 public/app/headers/es6-promise/es6-promise.d.ts diff --git a/package.json b/package.json index b245bf540da..60467015be0 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,6 @@ "url": "http://github.com/grafana/grafana.git" }, "devDependencies": { - "angular2": "2.0.0-beta.12", "zone.js": "^0.6.6", "autoprefixer": "^6.3.3", "es6-promise": "^3.0.2", @@ -54,7 +53,7 @@ "mocha": "2.3.4", "phantomjs-prebuilt": "^2.1.3", "reflect-metadata": "0.1.2", - "rxjs": "5.0.0-beta.2", + "rxjs": "5.0.0-beta.4", "sass-lint": "^1.5.0", "systemjs": "0.19.24" }, diff --git a/public/app/core/time_series2.ts b/public/app/core/time_series2.ts index f5fcf5bd50c..e0a3dd47b4e 100644 --- a/public/app/core/time_series2.ts +++ b/public/app/core/time_series2.ts @@ -170,7 +170,7 @@ export default class TimeSeries { } isMsResolutionNeeded() { - for (var i = 0; i -/// +/// declare var System: any; diff --git a/public/app/headers/es6-promise/es6-promise.d.ts b/public/app/headers/es6-promise/es6-promise.d.ts deleted file mode 100644 index 86c82273a0d..00000000000 --- a/public/app/headers/es6-promise/es6-promise.d.ts +++ /dev/null @@ -1,73 +0,0 @@ -// Type definitions for es6-promise -// Project: https://github.com/jakearchibald/ES6-Promise -// Definitions by: François de Campredon , vvakame -// Definitions: https://github.com/borisyankov/DefinitelyTyped - -interface Thenable { - then(onFulfilled?: (value: R) => U | Thenable, onRejected?: (error: any) => U | Thenable): Thenable; - then(onFulfilled?: (value: R) => U | Thenable, onRejected?: (error: any) => void): Thenable; -} - -declare class Promise implements Thenable { - /** - * If you call resolve in the body of the callback passed to the constructor, - * your promise is fulfilled with result object passed to resolve. - * If you call reject your promise is rejected with the object passed to resolve. - * For consistency and debugging (eg stack traces), obj should be an instanceof Error. - * Any errors thrown in the constructor callback will be implicitly passed to reject(). - */ - constructor(callback: (resolve : (value?: R | Thenable) => void, reject: (error?: any) => void) => void); - - /** - * onFulfilled is called when/if "promise" resolves. onRejected is called when/if "promise" rejects. - * Both are optional, if either/both are omitted the next onFulfilled/onRejected in the chain is called. - * Both callbacks have a single parameter , the fulfillment value or rejection reason. - * "then" returns a new promise equivalent to the value you return from onFulfilled/onRejected after being passed through Promise.resolve. - * If an error is thrown in the callback, the returned promise rejects with that error. - * - * @param onFulfilled called when/if "promise" resolves - * @param onRejected called when/if "promise" rejects - */ - then(onFulfilled?: (value: R) => U | Thenable, onRejected?: (error: any) => U | Thenable): Promise; - then(onFulfilled?: (value: R) => U | Thenable, onRejected?: (error: any) => void): Promise; - - /** - * Sugar for promise.then(undefined, onRejected) - * - * @param onRejected called when/if "promise" rejects - */ - catch(onRejected?: (error: any) => U | Thenable): Promise; -} - -declare module Promise { - /** - * Make a new promise from the thenable. - * A thenable is promise-like in as far as it has a "then" method. - */ - function resolve(value?: R | Thenable): Promise; - - /** - * Make a promise that rejects to obj. For consistency and debugging (eg stack traces), obj should be an instanceof Error - */ - function reject(error: any): Promise; - - /** - * Make a promise that fulfills when every item in the array fulfills, and rejects if (and when) any item rejects. - * the array passed to all can be a mixture of promise-like objects and other objects. - * The fulfillment value is an array (in order) of fulfillment values. The rejection value is the first rejection value. - */ - function all(promises: (R | Thenable)[]): Promise; - - /** - * Make a Promise that fulfills when any item fulfills, and rejects if any item rejects. - */ - function race(promises: (R | Thenable)[]): Promise; -} - -declare module 'es6-promise' { - var foo: typeof Promise; // Temp variable to reference Promise in local context - module rsvp { - export var Promise: typeof foo; - } - export = rsvp; -} diff --git a/public/app/headers/es6-shim/es6-shim.d.ts b/public/app/headers/es6-shim/es6-shim.d.ts index 41f22997af5..265c19e08f9 100644 --- a/public/app/headers/es6-shim/es6-shim.d.ts +++ b/public/app/headers/es6-shim/es6-shim.d.ts @@ -1,7 +1,9 @@ +// Generated by typings +// Source: https://raw.githubusercontent.com/DefinitelyTyped/DefinitelyTyped/7de6c3dd94feaeb21f20054b9f30d5dabc5efabd/es6-shim/es6-shim.d.ts // Type definitions for es6-shim v0.31.2 // Project: https://github.com/paulmillr/es6-shim // Definitions by: Ron Buckton -// Definitions: https://github.com/borisyankov/DefinitelyTyped +// Definitions: https://github.com/DefinitelyTyped/DefinitelyTyped declare type PropertyKey = string | number | symbol; @@ -621,7 +623,7 @@ interface WeakSetConstructor { declare var WeakSet: WeakSetConstructor; -declare module Reflect { +declare namespace Reflect { function apply(target: Function, thisArgument: any, argumentsList: ArrayLike): any; function construct(target: Function, argumentsList: ArrayLike): any; function defineProperty(target: any, propertyKey: PropertyKey, attributes: PropertyDescriptor): boolean; @@ -649,7 +651,7 @@ declare module "es6-shim" { var WeakMap: WeakMapConstructor; var WeakSet: WeakSetConstructor; var Promise: PromiseConstructor; - module Reflect { + namespace Reflect { function apply(target: Function, thisArgument: any, argumentsList: ArrayLike): any; function construct(target: Function, argumentsList: ArrayLike): any; function defineProperty(target: any, propertyKey: PropertyKey, attributes: PropertyDescriptor): boolean; diff --git a/public/app/plugins/panel/graph/module.ts b/public/app/plugins/panel/graph/module.ts index a430be98662..aeb2aa5765a 100644 --- a/public/app/plugins/panel/graph/module.ts +++ b/public/app/plugins/panel/graph/module.ts @@ -216,6 +216,11 @@ class GraphCtrl extends MetricsPanelCtrl { } series.applySeriesOverrides(this.panel.seriesOverrides); + + if (seriesData.unit) { + this.panel.yaxes[series.yaxis-1].format = seriesData.unit; + } + return series; } diff --git a/public/test/core/utils/emitter_specs.ts b/public/test/core/utils/emitter_specs.ts index 6ab5f80fa0e..9bf94030274 100644 --- a/public/test/core/utils/emitter_specs.ts +++ b/public/test/core/utils/emitter_specs.ts @@ -23,8 +23,28 @@ describe("Emitter", () => { expect(sub1Called).to.be(true); expect(sub2Called).to.be(true); }); - }); + it('should handle errors', () => { + var events = new Emitter(); + var sub1Called = 0; + var sub2Called = 0; + + var sub1 = events.on('test', () => { + sub1Called++; + throw "hello"; + }); + + events.on('test', () => { + sub2Called++; + }); + + try { events.emit('test', null); } catch (_) { } + try { events.emit('test', null); } catch (_) {} + + expect(sub1Called).to.be(1); + expect(sub2Called).to.be(1); + }); + }); }); From 4d63b576f7614579807a668e217df86fa0f3594d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Torkel=20=C3=96degaard?= Date: Thu, 7 Apr 2016 19:47:48 -0400 Subject: [PATCH 2/2] tech(): put in a real event emitter instead of rxjs based on that was broken --- CHANGELOG.md | 14 ++-------- package.json | 1 + public/app/core/utils/emitter.ts | 37 ++++++------------------- public/app/headers/common.d.ts | 5 ++++ public/app/system.conf.js | 5 ++++ public/sass/utils/_utils.scss | 1 + public/test/core/utils/emitter_specs.ts | 8 +++--- public/test/test-main.js | 7 ++++- tasks/options/copy.js | 5 +--- 9 files changed, 33 insertions(+), 50 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2399eda7140..075f4758dd7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,13 +1,4 @@ -# 3.0.0-beta3 (unreleased) - -### Bug fixes -* **Postgres**: Fixed page render crash when using postgres, fixes [#4558](https://github.com/grafana/grafana/issues/4558) -* **Table panel**: Fixed table panel bug when trying to show annotations in table panel, fixes [#4563](https://github.com/grafana/grafana/issues/4563) -* **App Config**: Fixed app config issue showing content of other app config, fixes [#4575](https://github.com/grafana/grafana/issues/4575) -* **Graph Panel**: Fixed legend option max not updating, fixes [#4601](https://github.com/grafana/grafana/issues/4601) -* **Graph Panel**: Fixed issue where newly added graph panels shared same axes config, fixes [#4582](https://github.com/grafana/grafana/issues/4582) - -# 3.0.0-beta2 (2016-04-04) +# 3.0.0-beta2 (unreleased) ### New Features (introduces since 3.0-beta1) * **Preferences**: Set home dashboard on user and org level, closes [#1678](https://github.com/grafana/grafana/issues/1678) @@ -18,9 +9,8 @@ * **Dashboard**: Fixed dashboard panel layout for mobile devices, fixes [#4529](https://github.com/grafana/grafana/issues/4529) * **Table Panel**: Fixed issue with table panel sort, fixes [#4532](https://github.com/grafana/grafana/issues/4532) * **Page Load Crash**: A Datasource with null jsonData would make Grafana fail to load page, fixes [#4536](https://github.com/grafana/grafana/issues/4536) -* **Metrics tab**: Fix for missing datasource name in datasource selector, fixes [#4540](https://github.com/grafana/grafana/issues/4540) +* **Metrics tab**: Fix for missing datasource name in datasource selector, fixes [#4541](https://github.com/grafana/grafana/issues/4540) * **Graph**: Fix legend in table mode with series on right-y axis, fixes [#4551](https://github.com/grafana/grafana/issues/4551), [#1145](https://github.com/grafana/grafana/issues/1145) -* **Password**: Password reset link/page did not work, fixes [#4542](https://github.com/grafana/grafana/issues/4542) # 3.0.0-beta1 (2016-03-31) diff --git a/package.json b/package.json index 60467015be0..d0c5e0b42f3 100644 --- a/package.json +++ b/package.json @@ -67,6 +67,7 @@ }, "license": "Apache-2.0", "dependencies": { + "eventemitter3": "^1.2.0", "grunt-jscs": "~1.5.x", "grunt-sass-lint": "^0.1.0", "grunt-sync": "^0.4.1", diff --git a/public/app/core/utils/emitter.ts b/public/app/core/utils/emitter.ts index 5de9dc78cfa..5f3f61cca2e 100644 --- a/public/app/core/utils/emitter.ts +++ b/public/app/core/utils/emitter.ts @@ -1,6 +1,6 @@ /// -import {Subject} from 'vendor/npm/rxjs/Subject'; +import EventEmitter from 'eventemitter3'; var hasOwnProp = {}.hasOwnProperty; @@ -9,48 +9,27 @@ function createName(name) { } export class Emitter { - subjects: any; + emitter: any; constructor() { - this.subjects = {}; + this.emitter = new EventEmitter(); } emit(name, data?) { - var fnName = createName(name); - this.subjects[fnName] || (this.subjects[fnName] = new Subject()); - this.subjects[fnName].next(data); + this.emitter.emit(name, data); } on(name, handler, scope?) { - var fnName = createName(name); - this.subjects[fnName] || (this.subjects[fnName] = new Subject()); - var subscription = this.subjects[fnName].subscribe(handler); + this.emitter.on(name, handler); if (scope) { scope.$on('$destroy', function() { - subscription.unsubscribe(); + this.emitter.off(name, handler); }); } - - return subscription; - }; + } off(name, handler) { - var fnName = createName(name); - if (this.subjects[fnName]) { - this.subjects[fnName].dispose(); - delete this.subjects[fnName]; - } - } - - dispose() { - var subjects = this.subjects; - for (var prop in subjects) { - if (hasOwnProp.call(subjects, prop)) { - subjects[prop].dispose(); - } - } - - this.subjects = {}; + this.emitter.off(name, handler); } } diff --git a/public/app/headers/common.d.ts b/public/app/headers/common.d.ts index 7d4dd4b2512..654cdb8288d 100644 --- a/public/app/headers/common.d.ts +++ b/public/app/headers/common.d.ts @@ -47,3 +47,8 @@ declare module 'tether-drop' { var config: any; export default config; } + +declare module 'eventemitter3' { + var config: any; + export default config; +} diff --git a/public/app/system.conf.js b/public/app/system.conf.js index 16fdcd7e3d8..276988e5c34 100644 --- a/public/app/system.conf.js +++ b/public/app/system.conf.js @@ -4,6 +4,7 @@ System.config({ paths: { 'remarkable': 'vendor/npm/remarkable/dist/remarkable.js', 'tether': 'vendor/npm/tether/dist/js/tether.js', + 'eventemitter3': 'vendor/npm/eventemitter3/index.js', 'tether-drop': 'vendor/npm/tether-drop/dist/js/drop.js', 'moment': 'vendor/moment.js', "jquery": "vendor/jquery/dist/jquery.js", @@ -55,5 +56,9 @@ System.config({ deps: ['jquery'], exports: 'angular', }, + 'vendor/npm/eventemitter3/index.js': { + format: 'cjs', + exports: 'EventEmitter' + }, } }); diff --git a/public/sass/utils/_utils.scss b/public/sass/utils/_utils.scss index b97f1aee50d..055fe96a213 100644 --- a/public/sass/utils/_utils.scss +++ b/public/sass/utils/_utils.scss @@ -52,6 +52,7 @@ button.close { .pull-right { float: right !important; } + .pull-left { float: left !important; } diff --git a/public/test/core/utils/emitter_specs.ts b/public/test/core/utils/emitter_specs.ts index 9bf94030274..f7076c46719 100644 --- a/public/test/core/utils/emitter_specs.ts +++ b/public/test/core/utils/emitter_specs.ts @@ -24,12 +24,12 @@ describe("Emitter", () => { expect(sub2Called).to.be(true); }); - it('should handle errors', () => { + it.only('should handle errors', () => { var events = new Emitter(); var sub1Called = 0; var sub2Called = 0; - var sub1 = events.on('test', () => { + events.on('test', () => { sub1Called++; throw "hello"; }); @@ -41,8 +41,8 @@ describe("Emitter", () => { try { events.emit('test', null); } catch (_) { } try { events.emit('test', null); } catch (_) {} - expect(sub1Called).to.be(1); - expect(sub2Called).to.be(1); + expect(sub1Called).to.be(2); + expect(sub2Called).to.be(0); }); }); }); diff --git a/public/test/test-main.js b/public/test/test-main.js index 5cc7b25dd6c..d40955022fe 100644 --- a/public/test/test-main.js +++ b/public/test/test-main.js @@ -10,6 +10,7 @@ baseURL: '/base/', defaultJSExtensions: true, paths: { + 'eventemitter3': 'vendor/npm/eventemitter3/index.js', 'tether': 'vendor/npm/tether/dist/js/tether.js', 'tether-drop': 'vendor/npm/tether-drop/dist/js/drop.js', 'moment': 'vendor/moment.js', @@ -58,7 +59,11 @@ 'vendor/angular-mocks/angular-mocks.js': { format: 'global', deps: ['angular'], - } + }, + 'vendor/npm/eventemitter3/index.js': { + format: 'cjs', + exports: 'EventEmitter' + }, } }); diff --git a/tasks/options/copy.js b/tasks/options/copy.js index 59a36e6153a..48dcc1dba66 100644 --- a/tasks/options/copy.js +++ b/tasks/options/copy.js @@ -19,10 +19,7 @@ module.exports = function(config) { cwd: './node_modules', expand: true, src: [ - 'angular2/bundles/*.js', - 'angular2/*.d.ts', - 'angular2/typings/**/*', - 'angular2/manual_typings/**/*', + 'eventemitter3/*.js', 'systemjs/dist/*.js', 'es6-promise/**/*', 'es6-shim/*.js',