From 12c854b7ac247e96905770ab710db8a9d1aa670d Mon Sep 17 00:00:00 2001 From: Monroe Ekilah Date: Tue, 29 Oct 2019 12:32:20 -0700 Subject: [PATCH] allow passing WeekdayStr to byweekday like the types suggest is possible --- src/helpers.ts | 6 ++++++ src/parseoptions.ts | 19 ++++++++++++------- src/weekday.ts | 8 ++++++-- test/parseoptions.test.ts | 33 +++++++++++++++++++++++++++++++++ 4 files changed, 57 insertions(+), 9 deletions(-) diff --git a/src/helpers.ts b/src/helpers.ts index af458c8d..33cc9cfd 100644 --- a/src/helpers.ts +++ b/src/helpers.ts @@ -2,6 +2,8 @@ // Helper functions // ============================================================================= +import { ALL_WEEKDAYS, WeekdayStr } from './weekday' + export const isPresent = function(value?: T | null | undefined): value is T { return value !== null && value !== undefined } @@ -10,6 +12,10 @@ export const isNumber = function (value?: any): value is number { return typeof value === 'number' } +export const isWeekdayStr = function (value?: any): value is WeekdayStr { + return ALL_WEEKDAYS.indexOf(value) >= 0 +} + export const isArray = Array.isArray /** diff --git a/src/parseoptions.ts b/src/parseoptions.ts index 4c83c572..a7112d38 100644 --- a/src/parseoptions.ts +++ b/src/parseoptions.ts @@ -1,8 +1,8 @@ import { Options, ParsedOptions, freqIsDailyOrGreater } from './types' -import { includes, notEmpty, isPresent, isNumber, isArray } from './helpers' +import { includes, notEmpty, isPresent, isNumber, isArray, isWeekdayStr } from './helpers' import RRule, { defaultKeys, DEFAULT_OPTIONS } from './rrule' import dateutil from './dateutil' -import { Weekday } from './weekday' +import { ALL_WEEKDAYS, Weekday } from './weekday' import { Time } from './datetime' export function initializeOptions (options: Partial) { @@ -139,6 +139,9 @@ export function parseOptions (options: Partial) { } else if (isNumber(opts.byweekday)) { opts.byweekday = [opts.byweekday] opts.bynweekday = null + } else if (isWeekdayStr(opts.byweekday)) { + opts.byweekday = [Weekday.fromStr(opts.byweekday).weekday] + opts.bynweekday = null } else if (opts.byweekday instanceof Weekday) { if (!opts.byweekday.n || opts.freq > RRule.MONTHLY) { opts.byweekday = [opts.byweekday.weekday] @@ -148,7 +151,7 @@ export function parseOptions (options: Partial) { opts.byweekday = null } } else { - const byweekday = [] + const byweekday: number[] = [] const bynweekday = [] for (let i = 0; i < opts.byweekday.length; i++) { @@ -157,13 +160,15 @@ export function parseOptions (options: Partial) { if (isNumber(wday)) { byweekday.push(wday) continue + } else if (isWeekdayStr(wday)) { + byweekday.push(Weekday.fromStr(wday).weekday) + continue } - const wd = wday as Weekday - if (!wd.n || opts.freq > RRule.MONTHLY) { - byweekday.push(wd.weekday) + if (!wday.n || opts.freq > RRule.MONTHLY) { + byweekday.push(wday.weekday) } else { - bynweekday.push([wd.weekday, wd.n]) + bynweekday.push([wday.weekday, wday.n]) } } opts.byweekday = notEmpty(byweekday) ? byweekday : null diff --git a/src/weekday.ts b/src/weekday.ts index f8bffa8f..a9f879ae 100644 --- a/src/weekday.ts +++ b/src/weekday.ts @@ -3,7 +3,7 @@ // ============================================================================= export type WeekdayStr = 'MO' | 'TU' | 'WE' | 'TH' | 'FR' | 'SA' | 'SU' -const WDAYS: WeekdayStr[] = ['MO', 'TU', 'WE', 'TH', 'FR', 'SA', 'SU'] +export const ALL_WEEKDAYS: WeekdayStr[] = ['MO', 'TU', 'WE', 'TH', 'FR', 'SA', 'SU'] export class Weekday { public readonly weekday: number @@ -15,6 +15,10 @@ export class Weekday { this.n = n } + static fromStr (str: WeekdayStr): Weekday { + return new Weekday(ALL_WEEKDAYS.indexOf(str)) + } + // __call__ - Cannot call the object directly, do it through // e.g. RRule.TH.nth(-1) instead, nth (n: number) { @@ -28,7 +32,7 @@ export class Weekday { // __repr__ toString () { - let s: string = WDAYS[this.weekday] + let s: string = ALL_WEEKDAYS[this.weekday] if (this.n) s = (this.n > 0 ? '+' : '') + String(this.n) + s return s } diff --git a/test/parseoptions.test.ts b/test/parseoptions.test.ts index a9c52e25..d4326513 100644 --- a/test/parseoptions.test.ts +++ b/test/parseoptions.test.ts @@ -1,5 +1,6 @@ import { parseOptions } from '../src/parseoptions' import { expect } from 'chai' +import RRule from '../src' describe('TZID', () => { it('leaves null when null', () => { @@ -13,3 +14,35 @@ describe('TZID', () => { expect(options.parsedOptions.tzid).to.equal('America/Los_Angeles') }) }) + +describe('byweekday', () => { + it('works with a single numeric day', () => { + const options = parseOptions({ byweekday: 1 }) + expect(options.parsedOptions.byweekday).to.eql([1]) + }) + + it('works with a single Weekday day', () => { + const options = parseOptions({ byweekday: RRule.TU }) + expect(options.parsedOptions.byweekday).to.eql([1]) + }) + + it('works with a single string day', () => { + const options = parseOptions({ byweekday: 'TU' }) + expect(options.parsedOptions.byweekday).to.eql([1]) + }) + + it('works with a multiple numeric days', () => { + const options = parseOptions({ byweekday: [1, 2] }) + expect(options.parsedOptions.byweekday).to.eql([1, 2]) + }) + + it('works with a multiple Weekday days', () => { + const options = parseOptions({ byweekday: [RRule.TU, RRule.WE] }) + expect(options.parsedOptions.byweekday).to.eql([1, 2]) + }) + + it('works with a multiple string days', () => { + const options = parseOptions({ byweekday: ['TU', 'WE'] }) + expect(options.parsedOptions.byweekday).to.eql([1, 2]) + }) +})