Skip to content
This repository has been archived by the owner on Nov 28, 2022. It is now read-only.

Handle manual timezone override #149

Merged
merged 1 commit into from
Jul 26, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
61 changes: 61 additions & 0 deletions app/components/gh-timezone-select.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
import Component from 'ember-component';
import computed, {mapBy} from 'ember-computed';
import injectService from 'ember-service/inject';
import {invokeAction} from 'ember-invoke-action';

export default Component.extend({
classNames: ['form-group', 'for-select'],

activeTimezone: null,
availableTimezones: null,

clock: injectService(),

availableTimezoneNames: mapBy('availableTimezones', 'name'),

hasTimezoneOverride: computed('activeTimezone', 'availableTimezoneNames', function () {
let activeTimezone = this.get('activeTimezone');
let availableTimezoneNames = this.get('availableTimezoneNames');

return !availableTimezoneNames.contains(activeTimezone);
}),

selectedTimezone: computed('activeTimezone', 'availableTimezones', 'hasTimezoneOverride', function () {
let hasTimezoneOverride = this.get('hasTimezoneOverride');
let activeTimezone = this.get('activeTimezone');
let availableTimezones = this.get('availableTimezones');

if (hasTimezoneOverride) {
return {name: '', label: ''};
}

return availableTimezones
.filterBy('name', activeTimezone)
.get('firstObject');
}),

selectableTimezones: computed('availableTimezones', 'hasTimezoneOverride', function () {
let hasTimezoneOverride = this.get('hasTimezoneOverride');
let availableTimezones = this.get('availableTimezones');

if (hasTimezoneOverride) {
return [{name: '', label: ''}, ...availableTimezones];
}

return availableTimezones;
}),

localTime: computed('hasTimezoneOverride', 'activeTimezone', 'selectedTimezone', 'clock.second', function () {
let hasTimezoneOverride = this.get('hasTimezoneOverride');
let timezone = hasTimezoneOverride ? this.get('activeTimezone') : this.get('selectedTimezone.name');

this.get('clock.second');
return timezone ? moment().tz(timezone).format('HH:mm:ss') : moment().utc().format('HH:mm:ss');
}),

actions: {
setTimezone(timezone) {
invokeAction(this, 'update', timezone);
}
}
});
16 changes: 0 additions & 16 deletions app/controllers/settings/general.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ export default Controller.extend(SettingsSaveMixin, {
config: injectService(),
_scratchFacebook: null,
_scratchTwitter: null,
clock: injectService(),

selectedTheme: computed('model.activeTheme', 'themes', function () {
let activeTheme = this.get('model.activeTheme');
Expand All @@ -33,15 +32,6 @@ export default Controller.extend(SettingsSaveMixin, {
return selectedTheme;
}),

selectedTimezone: computed('model.activeTimezone', 'availableTimezones', function () {
let activeTimezone = this.get('model.activeTimezone');
let availableTimezones = this.get('availableTimezones');

return availableTimezones
.filterBy('name', activeTimezone)
.get('firstObject');
}),

logoImageSource: computed('model.logo', function () {
return this.get('model.logo') || '';
}),
Expand All @@ -50,12 +40,6 @@ export default Controller.extend(SettingsSaveMixin, {
return this.get('model.cover') || '';
}),

localTime: computed('selectedTimezone', 'clock.second', function () {
let timezone = this.get('selectedTimezone.name');
this.get('clock.second');
return timezone ? moment().tz(timezone).format('HH:mm:ss') : moment().utc().format('HH:mm:ss');
}),

isDatedPermalinks: computed('model.permalinks', {
set(key, value) {
this.set('model.permalinks', value ? '/:year/:month/:day/:slug/' : '/:slug/');
Expand Down
16 changes: 16 additions & 0 deletions app/templates/components/gh-timezone-select.hbs
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
<label for="activeTimezone">Timezone</label>
<span class="gh-select" data-select-text="{{selectedTimezone.label}}" tabindex="0">
{{gh-select-native
id="activeTimezone"
name="general[activeTimezone]"
content=selectableTimezones
optionValuePath="name"
optionLabelPath="label"
selection=selectedTimezone
action="setTimezone"
}}
</span>
{{#if hasTimezoneOverride}}
<p>Your timezone has been automatically set to {{activeTimezone}}.</p>
{{/if}}
<p>The local time here is currently {{localTime}}</p>
19 changes: 4 additions & 15 deletions app/templates/settings/general.hbs
Original file line number Diff line number Diff line change
Expand Up @@ -113,21 +113,10 @@
{{/gh-form-group}}
</div>

<div class="form-group for-select">
<label for="activeTimezone">Timezone</label>
<span class="gh-select" data-select-text="{{selectedTimezone.label}}" tabindex="0">
{{gh-select-native
id="activeTimezone"
name="general[activeTimezone]"
content=availableTimezones
optionValuePath="name"
optionLabelPath="label"
selection=selectedTimezone
action="setTimezone"
}}
</span>
<p>The local time here is currently {{localTime}}</p>
</div>
{{gh-timezone-select
activeTimezone=model.activeTimezone
availableTimezones=availableTimezones
update=(action "setTimezone")}}

<div class="form-group for-checkbox">
<label for="isPrivate">Make this blog private</label>
Expand Down
78 changes: 78 additions & 0 deletions tests/integration/components/gh-timezone-select-test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
/* jshint expr:true */
import { expect } from 'chai';
import {
describeComponent,
it
} from 'ember-mocha';
import hbs from 'htmlbars-inline-precompile';
import run from 'ember-runloop';
import wait from 'ember-test-helpers/wait';
import sinon from 'sinon';

describeComponent(
'gh-timezone-select',
'Integration: Component: gh-timezone-select',
{
integration: true
},
function() {
beforeEach(function () {
this.set('availableTimezones', [
{name: 'Pacific/Pago_Pago', label: '(GMT -11:00) Midway Island, Samoa'},
{name: 'Etc/UTC', label: '(GMT) UTC'},
{name: 'Pacific/Kwajalein', label: '(GMT +12:00) International Date Line West'}
]);
this.set('activeTimezone', 'Etc/UTC');
});

it('renders', function () {
this.render(hbs`{{gh-timezone-select
availableTimezones=availableTimezones
activeTimezone=activeTimezone}}`);

expect(this.$(), 'top-level elements').to.have.length(1);
expect(this.$('option'), 'number of options').to.have.length(3);
expect(this.$('select').val(), 'selected option value').to.equal('Etc/UTC');
});

it('handles an unknown timezone', function () {
this.set('activeTimezone', 'Europe/London');

this.render(hbs`{{gh-timezone-select
availableTimezones=availableTimezones
activeTimezone=activeTimezone}}`);

// we have an additional blank option at the top
expect(this.$('option'), 'number of options').to.have.length(4);
// blank option is selected
expect(this.$('select').val(), 'selected option value').to.equal('');
// we indicate the manual override
expect(this.$('p').text()).to.match(/Your timezone has been automatically set to Europe\/London/);
});

it('triggers update action on change', function (done) {
let update = sinon.spy();
this.set('update', update);

this.render(hbs`{{gh-timezone-select
availableTimezones=availableTimezones
activeTimezone=activeTimezone
update=(action update)}}`);

run(() => {
this.$('select').val('Pacific/Pago_Pago').change();
});

wait().then(() => {
expect(update.calledOnce, 'update was called once').to.be.true;
expect(update.firstCall.args[0].name, 'update was passed new timezone')
.to.equal('Pacific/Pago_Pago');
done();
});
});

// TODO: mock clock service, fake the time, test we have the correct
// local time and it changes alongside selection changes
it('renders local time');
}
);