]> git.ipfire.org Git - thirdparty/Chart.js.git/commitdiff
Type fixes for time adapters (#12010)
authorJosh Kelley <joshkel@gmail.com>
Wed, 29 Jan 2025 10:32:29 +0000 (05:32 -0500)
committerGitHub <noreply@github.com>
Wed, 29 Jan 2025 10:32:29 +0000 (11:32 +0100)
Specific changes:

* `formats` is defined as an arbitrary record.  In practice, it maps from `TimeUnit` and `'datetime'` to the specific date library's format strings.
* `parse` and `format` were defined as requiring `TimeUnit`, but they actually take date library format strings.  (E.g., it's up to the caller to look up format strings via `formats()` or user parameters.)
* `endOf` is never passed `isoWeek` (`isoWeek` isn't a normal `TimeUnit`, it's only used as a special case to `startOf`), and [chartjs-adapter-date-fns](https://github.com/chartjs/chartjs-adapter-date-fns/blob/v3.0.0/src/index.js#L101) doesn't support it.
* The constructor's options parameter is optional.
* `weekday` is documented as allowing a boolean (true means to start on Monday).
* `export default { _date: DateAdapterBase }` meant that `new _date()` returns a `DateAdapterBase` instance, whose methods take no parameters.  Since it can be overridden at runtime, I replaced it with a more generic constructor + static methods.

src/core/core.adapters.ts
src/scales/scale.time.js

index 6c9b2b03248b59b81137086e5b2277283c68d532..282d13699f17509f27dda3dc30c5c69f6e578835 100644 (file)
@@ -19,19 +19,19 @@ export interface DateAdapter<T extends AnyObject = AnyObject> {
    * Returns a map of time formats for the supported formatting units defined
    * in Unit as well as 'datetime' representing a detailed date/time string.
    */
-  formats(this: DateAdapter<T>): Record<string, string>;
+  formats(this: DateAdapter<T>): Record<TimeUnit | 'datetime', string>;
   /**
    * Parses the given `value` and return the associated timestamp.
    * @param value - the value to parse (usually comes from the data)
    * @param [format] - the expected data format
    */
-  parse(this: DateAdapter<T>, value: unknown, format?: TimeUnit): number | null;
+  parse(this: DateAdapter<T>, value: unknown, format?: string): number | null;
   /**
    * Returns the formatted date in the specified `format` for a given `timestamp`.
    * @param timestamp - the timestamp to format
    * @param format - the date/time token
    */
-  format(this: DateAdapter<T>, timestamp: number, format: TimeUnit): string;
+  format(this: DateAdapter<T>, timestamp: number, format: string): string;
   /**
    * Adds the specified `amount` of `unit` to the given `timestamp`.
    * @param timestamp - the input timestamp
@@ -53,13 +53,13 @@ export interface DateAdapter<T extends AnyObject = AnyObject> {
    * @param [weekday] - the ISO day of the week with 1 being Monday
    * and 7 being Sunday (only needed if param *unit* is `isoWeek`).
    */
-  startOf(this: DateAdapter<T>, timestamp: number, unit: TimeUnit | 'isoWeek', weekday?: number): number;
+  startOf(this: DateAdapter<T>, timestamp: number, unit: TimeUnit | 'isoWeek', weekday?: number | boolean): number;
   /**
    * Returns end of `unit` for the given `timestamp`.
    * @param timestamp - the input timestamp
    * @param unit - the unit as string
    */
-  endOf(this: DateAdapter<T>, timestamp: number, unit: TimeUnit | 'isoWeek'): number;
+  endOf(this: DateAdapter<T>, timestamp: number, unit: TimeUnit): number;
 }
 
 function abstract<T = void>(): T {
@@ -92,14 +92,14 @@ class DateAdapterBase implements DateAdapter {
 
   readonly options: AnyObject;
 
-  constructor(options: AnyObject) {
+  constructor(options?: AnyObject) {
     this.options = options || {};
   }
 
   // eslint-disable-next-line @typescript-eslint/no-empty-function
   init() {}
 
-  formats(): Record<string, string> {
+  formats(): Record<TimeUnit | 'datetime', string> {
     return abstract();
   }
 
@@ -129,5 +129,10 @@ class DateAdapterBase implements DateAdapter {
 }
 
 export default {
-  _date: DateAdapterBase
+  _date: DateAdapterBase as {
+    new (options?: AnyObject): DateAdapter;
+    override<T extends AnyObject = AnyObject>(
+      members: Partial<Omit<DateAdapter<T>, 'options'>>
+    ): void;
+  }
 };
index 184937466598b49a7e06fcd65fbfd844fa30cbce..f82d43ad72d01f63f4fb7baa43afc34f71c88ab6 100644 (file)
@@ -59,7 +59,7 @@ function parse(scale, input) {
   // Only parse if it's not a timestamp already
   if (!isFinite(value)) {
     value = typeof parser === 'string'
-      ? adapter.parse(value, /** @type {Unit} */ (parser))
+      ? adapter.parse(value, parser)
       : adapter.parse(value);
   }