1
0
mirror of https://github.com/flarum/core.git synced 2025-08-30 11:30:21 +02:00

Compare commits

..

2 Commits

Author SHA1 Message Date
Alexander Skvortsov
31a2f67462 Apply fixes from StyleCI
[ci skip] [skip ci]
2021-12-12 19:38:25 +00:00
Alexander Skvortsov
3da7d7d221 Add server metadata in writable paths errors 2021-12-12 14:38:08 -05:00
266 changed files with 3064 additions and 4729 deletions

1
.gitattributes vendored
View File

@@ -13,6 +13,5 @@ tests export-ignore
js/dist/* -diff js/dist/* -diff
js/dist/* linguist-generated js/dist/* linguist-generated
js/dist-typings/* linguist-generated js/dist-typings/* linguist-generated
js/yarn.lock -diff
* text=auto eol=lf * text=auto eol=lf

View File

@@ -49,7 +49,7 @@ jobs:
working-directory: ./js working-directory: ./js
- name: Typecheck - name: Typecheck
run: yarn run check-typings run: yarn run check-typings || true # REMOVE THIS ONCE TYPE SAFETY REACHED
working-directory: ./js working-directory: ./js
type-coverage: type-coverage:

View File

@@ -9,6 +9,7 @@
<a href="https://github.styleci.io/repos/28257573"><img src="https://github.styleci.io/repos/28257573/shield?style=flat" alt="StyleCI"></a> <a href="https://github.styleci.io/repos/28257573"><img src="https://github.styleci.io/repos/28257573/shield?style=flat" alt="StyleCI"></a>
</p> </p>
## About Flarum ## About Flarum
**[Flarum](https://flarum.org/) is a delightfully simple discussion platform for your website.** It's fast and easy to use, with all the features you need to run a successful community. It is designed to be: **[Flarum](https://flarum.org/) is a delightfully simple discussion platform for your website.** It's fast and easy to use, with all the features you need to run a successful community. It is designed to be:
@@ -19,15 +20,13 @@
* **Powerful and extensible.** Customize, extend, and integrate Flarum to suit your community. Flarums architecture is amazingly flexible, with a powerful Extension API. * **Powerful and extensible.** Customize, extend, and integrate Flarum to suit your community. Flarums architecture is amazingly flexible, with a powerful Extension API.
![Screenshot of a Flarum instance, showing multiple discussions and tags.](https://flarum.org/assets/img/home-screenshot.png)
## Installation ## Installation
This repository contains Flarum's core code. If you want to set up a forum, visit the [Flarum skeleton repository](https://github.com/flarum/flarum). For support, refer to the [documentation](https://docs.flarum.org/), and ask questions on [Flarum Discuss](https://discuss.flarum.org/) (our community forum) or [Discord server](https://flarum.org/discord/). This repository contains Flarum's core code. If you want to set up a forum, visit the [Flarum skeleton repository](https://github.com/flarum/flarum).
## Contributing ## Contributing
Thank you for considering contributing to Flarum! Please read the **[Contributing guide](https://docs.flarum.org/contributing)** to learn how you can help. Thank you for considering contributing to Flarum! Please read the **[Contributing guide](https://flarum.org/docs/contributing.html)** to learn how you can help.
## Security Vulnerabilities ## Security Vulnerabilities

File diff suppressed because one or more lines are too long

View File

@@ -1,3 +1,2 @@
yarnPath: .yarn/releases/yarn-3.1.0.cjs
nodeLinker: node-modules nodeLinker: node-modules
yarnPath: .yarn/releases/yarn-3.1.1.cjs

View File

@@ -21,20 +21,7 @@ declare type KeysOfType<Type extends object, Match> = {
*/ */
declare type KeyOfType<Type extends object, Match> = KeysOfType<Type, Match>[keyof Type]; declare type KeyOfType<Type extends object, Match> = KeysOfType<Type, Match>[keyof Type];
type Component<A> = import('mithril').Component<A>; declare type VnodeElementTag<Attrs = Record<string, unknown>, State = Record<string, unknown>> = string | ComponentTypes<Attrs, State>;
declare type ComponentClass<Attrs = Record<string, unknown>, C extends Component<Attrs> = Component<Attrs>> = {
new (...args: any[]): Component<Attrs>;
prototype: C;
};
/**
* Unfortunately, TypeScript only supports strings and classes for JSX tags.
* Therefore, our type definition should only allow for those two types.
*
* @see https://github.com/microsoft/TypeScript/issues/14789#issuecomment-412247771
*/
declare type VnodeElementTag<Attrs = Record<string, unknown>, C extends Component<Attrs> = Component<Attrs>> = string | ComponentClass<Attrs, C>;
/** /**
* @deprecated Please import `app` from a namespace instead of using it as a global variable. * @deprecated Please import `app` from a namespace instead of using it as a global variable.
@@ -59,17 +46,6 @@ declare const app: never;
declare const m: import('mithril').Static; declare const m: import('mithril').Static;
declare const dayjs: typeof import('dayjs'); declare const dayjs: typeof import('dayjs');
/**
* From https://github.com/lokesh/color-thief/issues/188
*/
declare module 'color-thief-browser' {
type Color = [number, number, number];
export default class ColorThief {
getColor: (img: HTMLImageElement | null) => Color;
getPalette: (img: HTMLImageElement | null) => Color[];
}
}
type ESModule = { __esModule: true; [key: string]: unknown }; type ESModule = { __esModule: true; [key: string]: unknown };
/** /**

View File

@@ -35,7 +35,7 @@ export default class AdminApplication extends Application {
history: { history: {
canGoBack: () => boolean; canGoBack: () => boolean;
getPrevious: () => void; getPrevious: () => void;
backUrl: () => string; backUrl: () => any;
back: () => void; back: () => void;
}; };
/** /**

View File

@@ -4,8 +4,8 @@ declare var _default: {
Store: typeof import("../common/Store").default; Store: typeof import("../common/Store").default;
'utils/BasicEditorDriver': typeof import("../common/utils/BasicEditorDriver").default; 'utils/BasicEditorDriver': typeof import("../common/utils/BasicEditorDriver").default;
'utils/evented': { 'utils/evented': {
handlers: Record<string, unknown>; handlers: Object;
getHandlers(event: string): Function[]; getHandlers(event: string): any[];
trigger(event: string, ...args: any[]): void; trigger(event: string, ...args: any[]): void;
on(event: string, handler: Function): void; on(event: string, handler: Function): void;
one(event: string, handler: Function): void; one(event: string, handler: Function): void;

View File

@@ -5,9 +5,9 @@ export default class AdminNav extends Component<import("../../common/Component")
/** /**
* Build an item list of main links to show in the admin navigation. * Build an item list of main links to show in the admin navigation.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
extensionItems(): ItemList<any>; extensionItems(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";

View File

@@ -2,8 +2,8 @@ import type Mithril from 'mithril';
import Page, { IPageAttrs } from '../../common/components/Page'; import Page, { IPageAttrs } from '../../common/components/Page';
import Stream from '../../common/utils/Stream'; import Stream from '../../common/utils/Stream';
export interface AdminHeaderOptions { export interface AdminHeaderOptions {
title: Mithril.Children; title: string;
description: Mithril.Children; description: string;
icon: string; icon: string;
/** /**
* Will be used as the class for the AdminPage. * Will be used as the class for the AdminPage.

View File

@@ -7,12 +7,10 @@ export default class BasicsPage extends AdminPage<import("../../common/component
* Build a list of options for the default homepage. Each option must be an * Build a list of options for the default homepage. Each option must be an
* object with `path` and `label` properties. * object with `path` and `label` properties.
* *
* @return {ItemList<{ path: string, label: import('mithril').Children }>} * @return {ItemList}
* @public
*/ */
homePageItems(): ItemList<{ public homePageItems(): ItemList<any>;
path: string;
label: import('mithril').Children;
}>;
} }
import AdminPage from "./AdminPage"; import AdminPage from "./AdminPage";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -3,14 +3,14 @@ export default class DashboardWidget extends Component<import("../../common/Comp
/** /**
* Get the class name to apply to the widget. * Get the class name to apply to the widget.
* *
* @return {string} * @return {String}
*/ */
className(): string; className(): string;
/** /**
* Get the content of the widget. * Get the content of the widget.
* *
* @return {import('mithril').Children} * @return {VirtualElement}
*/ */
content(): import('mithril').Children; content(): any;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";

View File

@@ -8,9 +8,9 @@ export default class HeaderPrimary extends Component<import("../../common/Compon
/** /**
* Build an item list for the controls. * Build an item list for the controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -6,9 +6,9 @@ export default class HeaderSecondary extends Component<import("../../common/Comp
/** /**
* Build an item list for the controls. * Build an item list for the controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -1,8 +1,6 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> /// <reference path="../../../src/common/translator-icu-rich.d.ts" />
import Modal, { IInternalModalAttrs } from '../../common/components/Modal'; import Modal from '../../common/components/Modal';
export interface ILoadingModalAttrs extends IInternalModalAttrs { export default class LoadingModal<ModalAttrs = {}> extends Modal<ModalAttrs> {
}
export default class LoadingModal<ModalAttrs extends ILoadingModalAttrs = ILoadingModalAttrs> extends Modal<ModalAttrs> {
/** /**
* @inheritdoc * @inheritdoc
*/ */

View File

@@ -1,18 +1,8 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> export default class ReadmeModal extends Modal<import("../../common/components/Modal").IInternalModalAttrs> {
import Modal, { IInternalModalAttrs } from '../../common/components/Modal'; constructor();
import ExtensionReadme from '../models/ExtensionReadme'; name: any;
import type Mithril from 'mithril'; extName: any;
import type { Extension } from '../AdminApplication';
export interface IReadmeModalAttrs extends IInternalModalAttrs {
extension: Extension;
}
export default class ReadmeModal<CustomAttrs extends IReadmeModalAttrs = IReadmeModalAttrs> extends Modal<CustomAttrs> {
protected name: string;
protected extName: string;
protected readme: ExtensionReadme;
oninit(vnode: Mithril.Vnode<CustomAttrs, this>): void;
className(): string;
title(): import("@askvortsov/rich-icu-message-formatter").NestedStringArray;
content(): JSX.Element;
loadReadme(): Promise<void>; loadReadme(): Promise<void>;
readme: any;
} }
import Modal from "../../common/components/Modal";

View File

@@ -1,6 +1,5 @@
export default class StatusWidget extends DashboardWidget { export default class StatusWidget extends DashboardWidget {
items(): ItemList<any>; items(): ItemList<any>;
toolsItems(): ItemList<any>;
handleClearCache(e: any): void; handleClearCache(e: any): void;
} }
import DashboardWidget from "./DashboardWidget"; import DashboardWidget from "./DashboardWidget";

View File

@@ -13,16 +13,16 @@ export default class UploadImageButton extends Button<import("../../common/compo
/** /**
* After a successful upload/removal, reload the page. * After a successful upload/removal, reload the page.
* *
* @param {object} response * @param {Object} response
* @protected * @protected
*/ */
protected success(response: object): void; protected success(response: Object): void;
/** /**
* If upload/removal fails, stop loading. * If upload/removal fails, stop loading.
* *
* @param {object} response * @param {Object} response
* @protected * @protected
*/ */
protected failure(response: object): void; protected failure(response: Object): void;
} }
import Button from "../../common/components/Button"; import Button from "../../common/components/Button";

View File

@@ -1,5 +1,5 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> /// <reference path="../../../src/common/translator-icu-rich.d.ts" />
import type Mithril from 'mithril'; /// <reference types="mithril" />
import type User from '../../common/models/User'; import type User from '../../common/models/User';
import ItemList from '../../common/utils/ItemList'; import ItemList from '../../common/utils/ItemList';
import AdminPage from './AdminPage'; import AdminPage from './AdminPage';
@@ -7,11 +7,11 @@ declare type ColumnData = {
/** /**
* Column title * Column title
*/ */
name: Mithril.Children; name: String;
/** /**
* Component(s) to show for this column. * Component(s) to show for this column.
*/ */
content: (user: User) => Mithril.Children; content: (user: User) => JSX.Element;
}; };
/** /**
* Admin page which displays a paginated list of all users on the forum. * Admin page which displays a paginated list of all users on the forum.

View File

@@ -1,4 +1,4 @@
export default class ExtensionReadme extends Model { export default class ExtensionReadme extends Model {
content: () => any; content: any;
} }
import Model from "../../common/Model"; import Model from "../../common/Model";

View File

@@ -1,6 +1,6 @@
import ItemList from './utils/ItemList'; import ItemList from './utils/ItemList';
import Translator from './Translator'; import Translator from './Translator';
import Store, { ApiPayload, ApiResponsePlural, ApiResponseSingle } from './Store'; import Store from './Store';
import Session from './Session'; import Session from './Session';
import Drawer from './utils/Drawer'; import Drawer from './utils/Drawer';
import RequestError, { InternalFlarumRequestOptions } from './utils/RequestError'; import RequestError, { InternalFlarumRequestOptions } from './utils/RequestError';
@@ -12,7 +12,6 @@ import type DefaultResolver from './resolvers/DefaultResolver';
import type Mithril from 'mithril'; import type Mithril from 'mithril';
import type Component from './Component'; import type Component from './Component';
import type { ComponentAttrs } from './Component'; import type { ComponentAttrs } from './Component';
import Model, { SavedModelData } from './Model';
export declare type FlarumScreens = 'phone' | 'tablet' | 'desktop' | 'desktop-hd'; export declare type FlarumScreens = 'phone' | 'tablet' | 'desktop' | 'desktop-hd';
export declare type FlarumGenericRoute = RouteItem<any, any, any>; export declare type FlarumGenericRoute = RouteItem<any, any, any>;
export interface FlarumRequestOptions<ResponseType> extends Omit<Mithril.RequestOptions<ResponseType>, 'extract'> { export interface FlarumRequestOptions<ResponseType> extends Omit<Mithril.RequestOptions<ResponseType>, 'extract'> {
@@ -73,8 +72,6 @@ export interface RouteResolver<Attrs extends ComponentAttrs, Comp extends Compon
* *
* Returns the component class, and **not** a Vnode or JSX * Returns the component class, and **not** a Vnode or JSX
* expression. * expression.
*
* @see https://mithril.js.org/route.html#routeresolveronmatch
*/ */
onmatch(this: this, args: RouteArgs, requestedPath: string, route: string): { onmatch(this: this, args: RouteArgs, requestedPath: string, route: string): {
new (): Comp; new (): Comp;
@@ -82,14 +79,9 @@ export interface RouteResolver<Attrs extends ComponentAttrs, Comp extends Compon
/** /**
* A function which renders the provided component. * A function which renders the provided component.
* *
* If not specified, the route will default to rendering the
* component on its own, inside of a fragment.
*
* Returns a Mithril Vnode or other children. * Returns a Mithril Vnode or other children.
*
* @see https://mithril.js.org/route.html#routeresolverrender
*/ */
render?(this: this, vnode: Mithril.Vnode<Attrs, Comp>): Mithril.Children; render(this: this, vnode: Mithril.Vnode<Attrs, Comp>): Mithril.Children;
} }
/** /**
* The `App` class provides a container for an application, as well as various * The `App` class provides a container for an application, as well as various
@@ -167,10 +159,10 @@ export default class Application {
*/ */
drawer: Drawer; drawer: Drawer;
data: { data: {
apiDocument: ApiPayload | null; apiDocument: Record<string, unknown> | null;
locale: string; locale: string;
locales: Record<string, string>; locales: Record<string, string>;
resources: SavedModelData[]; resources: Record<string, unknown>[];
session: { session: {
userId: number; userId: number;
csrfToken: string; csrfToken: string;
@@ -198,8 +190,7 @@ export default class Application {
/** /**
* Get the API response document that has been preloaded into the application. * Get the API response document that has been preloaded into the application.
*/ */
preloadedApiDocument<M extends Model>(): ApiResponseSingle<M> | null; preloadedApiDocument(): Record<string, unknown> | null;
preloadedApiDocument<Ms extends Model[]>(): ApiResponsePlural<Ms[number]> | null;
/** /**
* Determine the current screen mode, based on our media queries. * Determine the current screen mode, based on our media queries.
*/ */
@@ -222,13 +213,11 @@ export default class Application {
* Make an AJAX request, handling any low-level errors that may occur. * Make an AJAX request, handling any low-level errors that may occur.
* *
* @see https://mithril.js.org/request.html * @see https://mithril.js.org/request.html
*
* @param options
* @return {Promise}
*/ */
request<ResponseType>(originalOptions: FlarumRequestOptions<ResponseType>): Promise<ResponseType>; request<ResponseType>(originalOptions: FlarumRequestOptions<ResponseType>): Promise<ResponseType | string>;
/**
* By default, show an error alert, and log the error to the console.
*/
protected requestErrorCatch<ResponseType>(error: RequestError, customErrorHandler: FlarumRequestOptions<ResponseType>['errorHandler']): Promise<never>;
protected requestErrorDefaultHandler(e: unknown, isDebug: boolean, formattedErrors: string[]): void;
private showDebug; private showDebug;
/** /**
* Construct a URL to the route with the given name. * Construct a URL to the route with the given name.

View File

@@ -28,8 +28,8 @@ export default abstract class Fragment {
* containing all of the `li` elements inside the DOM element of this * containing all of the `li` elements inside the DOM element of this
* fragment. * fragment.
* *
* @param [selector] a jQuery-compatible selector string * @param {String} [selector] a jQuery-compatible selector string
* @returns the jQuery object for the DOM node * @returns {jQuery} the jQuery object for the DOM node
* @final * @final
*/ */
$(selector?: string): JQuery; $(selector?: string): JQuery;

View File

@@ -1,147 +1,149 @@
import { FlarumRequestOptions } from './Application';
import Store, { ApiPayloadSingle, ApiResponseSingle, MetaInformation } from './Store';
export interface ModelIdentifier {
type: string;
id: string;
}
export interface ModelAttributes {
[key: string]: unknown;
}
export interface ModelRelationships {
[relationship: string]: {
data: ModelIdentifier | ModelIdentifier[];
};
}
export interface UnsavedModelData {
type?: string;
attributes?: ModelAttributes;
relationships?: ModelRelationships;
}
export interface SavedModelData {
type: string;
id: string;
attributes?: ModelAttributes;
relationships?: ModelRelationships;
}
export declare type ModelData = UnsavedModelData | SavedModelData;
export interface SaveRelationships {
[relationship: string]: Model | Model[];
}
export interface SaveAttributes {
[key: string]: unknown;
relationships?: SaveRelationships;
}
/** /**
* The `Model` class represents a local data resource. It provides methods to * The `Model` class represents a local data resource. It provides methods to
* persist changes via the API. * persist changes via the API.
*
* @abstract
*/ */
export default abstract class Model { export default class Model {
/**
* The resource object from the API.
*/
data: ModelData;
/**
* The time at which the model's data was last updated. Watching the value
* of this property is a fast way to retain/cache a subtree if data hasn't
* changed.
*/
freshness: Date;
/**
* Whether or not the resource exists on the server.
*/
exists: boolean;
/**
* The data store that this resource should be persisted to.
*/
protected store: Store;
/**
* @param data A resource object from the API.
* @param store The data store that this model should be persisted to.
*/
constructor(data?: ModelData, store?: Store);
/**
* Get the model's ID.
*
* @final
*/
id(): string | undefined;
/**
* Get one of the model's attributes.
*
* @final
*/
attribute<T = unknown>(attribute: string): T;
/**
* Merge new data into this model locally.
*
* @param data A resource object to merge into this model
*/
pushData(data: ModelData | {
relationships?: SaveRelationships;
}): this;
/**
* Merge new attributes into this model locally.
*
* @param attributes The attributes to merge.
*/
pushAttributes(attributes: ModelAttributes): void;
/**
* Merge new attributes into this model, both locally and with persistence.
*
* @param attributes The attributes to save. If a 'relationships' key
* exists, it will be extracted and relationships will also be saved.
*/
save(attributes: SaveAttributes, options?: Omit<FlarumRequestOptions<ApiPayloadSingle>, 'url'> & {
meta?: MetaInformation;
}): Promise<ApiResponseSingle<this>>;
/**
* Send a request to delete the resource.
*
* @param body Data to send along with the DELETE request.
*/
delete(body?: FlarumRequestOptions<void>['body'], options?: Omit<FlarumRequestOptions<void>, 'url'>): Promise<void>;
/**
* Construct a path to the API endpoint for this resource.
*/
protected apiEndpoint(): string;
protected copyData(): ModelData;
protected rawRelationship<M extends Model>(relationship: string): undefined | ModelIdentifier;
protected rawRelationship<M extends Model[]>(relationship: string): undefined | ModelIdentifier[];
/** /**
* Generate a function which returns the value of the given attribute. * Generate a function which returns the value of the given attribute.
* *
* @param transform A function to transform the attribute value * @param {String} name
* @param {function} [transform] A function to transform the attribute value
* @return {*}
* @public
*/ */
static attribute<T>(name: string): () => T; public static attribute(name: string, transform?: Function | undefined): any;
static attribute<T, O = unknown>(name: string, transform: (attr: O) => T): () => T;
/** /**
* Generate a function which returns the value of the given has-one * Generate a function which returns the value of the given has-one
* relationship. * relationship.
* *
* @return false if no information about the * @param {String} name
* @return {Model|Boolean|undefined} false if no information about the
* relationship exists; undefined if the relationship exists but the model * relationship exists; undefined if the relationship exists but the model
* has not been loaded; or the model if it has been loaded. * has not been loaded; or the model if it has been loaded.
* @public
*/ */
static hasOne<M extends Model>(name: string): () => M | false; public static hasOne(name: string): Model | boolean | undefined;
static hasOne<M extends Model | null>(name: string): () => M | null | false;
/** /**
* Generate a function which returns the value of the given has-many * Generate a function which returns the value of the given has-many
* relationship. * relationship.
* *
* @return false if no information about the relationship * @param {String} name
* @return {Array|Boolean} false if no information about the relationship
* exists; an array if it does, containing models if they have been * exists; an array if it does, containing models if they have been
* loaded, and undefined for those that have not. * loaded, and undefined for those that have not.
* @public
*/ */
static hasMany<M extends Model>(name: string): () => (M | undefined)[] | false; public static hasMany(name: string): any[] | boolean;
/** /**
* Transform the given value into a Date object. * Transform the given value into a Date object.
*
* @param {String} value
* @return {Date|null}
* @public
*/ */
static transformDate(value: string): Date; public static transformDate(value: string): Date | null;
static transformDate(value: string | null): Date | null;
static transformDate(value: string | undefined): Date | undefined;
static transformDate(value: string | null | undefined): Date | null | undefined;
/** /**
* Get a resource identifier object for the given model. * Get a resource identifier object for the given model.
*
* @param {Model} model
* @return {Object}
* @protected
*/ */
protected static getIdentifier(model: Model): ModelIdentifier; protected static getIdentifier(model: Model): Object;
/**
* @param {Object} data A resource object from the API.
* @param {Store} store The data store that this model should be persisted to.
* @public
*/
constructor(data?: Object, store?: any);
/**
* The resource object from the API.
*
* @type {Object}
* @public
*/
public data: Object;
/**
* The time at which the model's data was last updated. Watching the value
* of this property is a fast way to retain/cache a subtree if data hasn't
* changed.
*
* @type {Date}
* @public
*/
public freshness: Date;
/**
* Whether or not the resource exists on the server.
*
* @type {Boolean}
* @public
*/
public exists: boolean;
/**
* The data store that this resource should be persisted to.
*
* @type {Store}
* @protected
*/
protected store: any;
/**
* Get the model's ID.
*
* @return {Integer}
* @public
* @final
*/
public id(): any;
/**
* Get one of the model's attributes.
*
* @param {String} attribute
* @return {*}
* @public
* @final
*/
public attribute(attribute: string): any;
/**
* Merge new data into this model locally.
*
* @param {Object} data A resource object to merge into this model
* @public
*/
public pushData(data: Object): void;
/**
* Merge new attributes into this model locally.
*
* @param {Object} attributes The attributes to merge.
* @public
*/
public pushAttributes(attributes: Object): void;
/**
* Merge new attributes into this model, both locally and with persistence.
*
* @param {Object} attributes The attributes to save. If a 'relationships' key
* exists, it will be extracted and relationships will also be saved.
* @param {Object} [options]
* @return {Promise}
* @public
*/
public save(attributes: Object, options?: Object | undefined): Promise<any>;
/**
* Send a request to delete the resource.
*
* @param {Object} body Data to send along with the DELETE request.
* @param {Object} [options]
* @return {Promise}
* @public
*/
public delete(body: Object, options?: Object | undefined): Promise<any>;
/**
* Construct a path to the API endpoint for this resource.
*
* @return {String}
* @protected
*/
protected apiEndpoint(): string;
copyData(): any;
} }

View File

@@ -5,8 +5,10 @@ export declare type LoginParams = {
* The username/email * The username/email
*/ */
identification: string; identification: string;
/**
* Password
*/
password: string; password: string;
remember: boolean;
}; };
/** /**
* The `Session` class defines the current user session. It stores a reference * The `Session` class defines the current user session. It stores a reference

View File

@@ -1,127 +1,97 @@
import { FlarumRequestOptions } from './Application';
import Model, { ModelData, SavedModelData } from './Model';
export interface MetaInformation {
[key: string]: any;
}
export interface ApiQueryParamsSingle {
fields?: string[];
include?: string;
bySlug?: boolean;
meta?: MetaInformation;
}
export interface ApiQueryParamsPlural {
fields?: string[];
include?: string;
filter?: {
q: string;
[key: string]: string;
};
page?: {
offset?: number;
number?: number;
limit?: number;
size?: number;
};
sort?: string;
meta?: MetaInformation;
}
export declare type ApiQueryParams = ApiQueryParamsPlural | ApiQueryParamsSingle;
export interface ApiPayloadSingle {
data: SavedModelData;
included?: SavedModelData[];
meta?: MetaInformation;
}
export interface ApiPayloadPlural {
data: SavedModelData[];
included?: SavedModelData[];
links?: {
first: string;
next?: string;
prev?: string;
};
meta?: MetaInformation;
}
export declare type ApiPayload = ApiPayloadSingle | ApiPayloadPlural;
export declare type ApiResponseSingle<M extends Model> = M & {
payload: ApiPayloadSingle;
};
export declare type ApiResponsePlural<M extends Model> = M[] & {
payload: ApiPayloadPlural;
};
export declare type ApiResponse<M extends Model> = ApiResponseSingle<M> | ApiResponsePlural<M>;
interface ApiQueryRequestOptions<ResponseType> extends Omit<FlarumRequestOptions<ResponseType>, 'url'> {
}
interface StoreData {
[type: string]: Partial<Record<string, Model>>;
}
export declare function payloadIsPlural(payload: ApiPayload): payload is ApiPayloadPlural;
/** /**
* The `Store` class defines a local data store, and provides methods to * The `Store` class defines a local data store, and provides methods to
* retrieve data from the API. * retrieve data from the API.
*/ */
export default class Store { export default class Store {
constructor(models: any);
/** /**
* The local data store. A tree of resource types to IDs, such that * The local data store. A tree of resource types to IDs, such that
* accessing data[type][id] will return the model for that type/ID. * accessing data[type][id] will return the model for that type/ID.
*
* @type {Object}
* @protected
*/ */
protected data: StoreData; protected data: Object;
/** /**
* The model registry. A map of resource types to the model class that * The model registry. A map of resource types to the model class that
* should be used to represent resources of that type. * should be used to represent resources of that type.
*
* @type {Object}
* @public
*/ */
models: Record<string, typeof Model>; public models: Object;
constructor(models: Record<string, typeof Model>);
/** /**
* Push resources contained within an API payload into the store. * Push resources contained within an API payload into the store.
* *
* @return The model(s) representing the resource(s) contained * @param {Object} payload
* @return {Model|Model[]} The model(s) representing the resource(s) contained
* within the 'data' key of the payload. * within the 'data' key of the payload.
* @public
*/ */
pushPayload<M extends Model>(payload: ApiPayloadSingle): ApiResponseSingle<M>; public pushPayload(payload: Object): any | any[];
pushPayload<Ms extends Model[]>(payload: ApiPayloadPlural): ApiResponsePlural<Ms[number]>;
/** /**
* Create a model to represent a resource object (or update an existing one), * Create a model to represent a resource object (or update an existing one),
* and push it into the store. * and push it into the store.
* *
* @param data The resource object * @param {Object} data The resource object
* @return The model, or null if no model class has been * @return {Model|null} The model, or null if no model class has been
* registered for this resource type. * registered for this resource type.
* @public
*/ */
pushObject<M extends Model>(data: SavedModelData): M | null; public pushObject(data: Object): any | null;
pushObject<M extends Model>(data: SavedModelData, allowUnregistered: false): M;
/** /**
* Make a request to the API to find record(s) of a specific type. * Make a request to the API to find record(s) of a specific type.
*
* @param {String} type The resource type.
* @param {Integer|Integer[]|Object} [id] The ID(s) of the model(s) to retrieve.
* Alternatively, if an object is passed, it will be handled as the
* `query` parameter.
* @param {Object} [query]
* @param {Object} [options]
* @return {Promise}
* @public
*/ */
find<M extends Model>(type: string, params: ApiQueryParamsSingle): Promise<ApiResponseSingle<M>>; public find(type: string, id?: any | any[] | Object, query?: Object | undefined, options?: Object | undefined): Promise<any>;
find<Ms extends Model[]>(type: string, params: ApiQueryParamsPlural): Promise<ApiResponsePlural<Ms[number]>>;
find<M extends Model>(type: string, id: string, params?: ApiQueryParamsSingle, options?: ApiQueryRequestOptions<ApiPayloadSingle>): Promise<ApiResponseSingle<M>>;
find<Ms extends Model[]>(type: string, ids: string[], params?: ApiQueryParamsPlural, options?: ApiQueryRequestOptions<ApiPayloadPlural>): Promise<ApiResponsePlural<Ms[number]>>;
/** /**
* Get a record from the store by ID. * Get a record from the store by ID.
*
* @param {String} type The resource type.
* @param {Integer} id The resource ID.
* @return {Model}
* @public
*/ */
getById<M extends Model>(type: string, id: string): M | undefined; public getById(type: string, id: any): any;
/** /**
* Get a record from the store by the value of a model attribute. * Get a record from the store by the value of a model attribute.
* *
* @param type The resource type. * @param {String} type The resource type.
* @param key The name of the method on the model. * @param {String} key The name of the method on the model.
* @param value The value of the model attribute. * @param {*} value The value of the model attribute.
* @return {Model}
* @public
*/ */
getBy<M extends Model, T = unknown>(type: string, key: keyof M, value: T): M | undefined; public getBy(type: string, key: string, value: any): any;
/** /**
* Get all loaded records of a specific type. * Get all loaded records of a specific type.
*
* @param {String} type
* @return {Model[]}
* @public
*/ */
all<M extends Model>(type: string): M[]; public all(type: string): any[];
/** /**
* Remove the given model from the store. * Remove the given model from the store.
*
* @param {Model} model
*/ */
remove(model: Model): void; remove(model: any): void;
/** /**
* Create a new record of the given type. * Create a new record of the given type.
* *
* @param type The resource type * @param {String} type The resource type
* @param data Any data to initialize the model with * @param {Object} [data] Any data to initialize the model with
* @return {Model}
* @public
*/ */
createRecord<M extends Model>(type: string, data?: ModelData): M; public createRecord(type: string, data?: Object | undefined): any;
} }
export {};

View File

@@ -4,8 +4,8 @@ declare var _default: {
Store: typeof Store; Store: typeof Store;
'utils/BasicEditorDriver': typeof BasicEditorDriver; 'utils/BasicEditorDriver': typeof BasicEditorDriver;
'utils/evented': { 'utils/evented': {
handlers: Record<string, unknown>; handlers: Object;
getHandlers(event: string): Function[]; getHandlers(event: string): any[];
trigger(event: string, ...args: any[]): void; trigger(event: string, ...args: any[]): void;
on(event: string, handler: Function): void; on(event: string, handler: Function): void;
one(event: string, handler: Function): void; one(event: string, handler: Function): void;

View File

@@ -15,14 +15,14 @@ export default class Checkbox extends Component<import("../Component").Component
/** /**
* Get the template for the checkbox's display (tick/cross icon). * Get the template for the checkbox's display (tick/cross icon).
* *
* @return {import('mithril').Children} * @return {*}
* @protected * @protected
*/ */
protected getDisplay(): import('mithril').Children; protected getDisplay(): any;
/** /**
* Run a callback when the state of the checkbox is changed. * Run a callback when the state of the checkbox is changed.
* *
* @param {boolean} checked * @param {Boolean} checked
* @protected * @protected
*/ */
protected onchange(checked: boolean): void; protected onchange(checked: boolean): void;

View File

@@ -22,17 +22,17 @@ export default class Dropdown extends Component<import("../Component").Component
/** /**
* Get the template for the button. * Get the template for the button.
* *
* @return {import('mithril').Children} * @return {*}
* @protected * @protected
*/ */
protected getButton(children: any): import('mithril').Children; protected getButton(children: any): any;
/** /**
* Get the template for the button's content. * Get the template for the button's content.
* *
* @return {import('mithril').Children} * @return {*}
* @protected * @protected
*/ */
protected getButtonContent(children: any): import('mithril').Children; protected getButtonContent(children: any): any;
getMenu(items: any): JSX.Element; getMenu(items: any): JSX.Element;
} }
import Component from "../Component"; import Component from "../Component";

View File

@@ -1,31 +1,26 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> /**
import Modal, { IInternalModalAttrs } from './Modal'; * The `EditUserModal` component displays a modal dialog with a login form.
import ItemList from '../utils/ItemList'; */
import Stream from '../utils/Stream'; export default class EditUserModal extends Modal<import("./Modal").IInternalModalAttrs> {
import type Mithril from 'mithril'; constructor();
import type User from '../models/User'; username: Stream<any> | undefined;
import type { SaveAttributes } from '../Model'; email: Stream<any> | undefined;
export interface IEditUserModalAttrs extends IInternalModalAttrs { isEmailConfirmed: Stream<any> | undefined;
user: User; setPassword: Stream<boolean> | undefined;
} password: Stream<any> | undefined;
export default class EditUserModal<CustomAttrs extends IEditUserModalAttrs = IEditUserModalAttrs> extends Modal<CustomAttrs> { groups: {} | undefined;
protected username: Stream<string>; fields(): ItemList<any>;
protected email: Stream<string>;
protected isEmailConfirmed: Stream<boolean>;
protected setPassword: Stream<boolean>;
protected password: Stream<string>;
protected groups: Record<string, Stream<boolean>>;
oninit(vnode: Mithril.Vnode<CustomAttrs, this>): void;
className(): string;
title(): import("@askvortsov/rich-icu-message-formatter").NestedStringArray;
content(): JSX.Element;
fields(): ItemList<unknown>;
activate(): void; activate(): void;
data(): SaveAttributes; data(): {
onsubmit(e: SubmitEvent): void; relationships: {};
nonAdminEditingAdmin(): boolean | null; };
nonAdminEditingAdmin(): any;
/** /**
* @internal * @internal
* @protected
*/ */
protected userIsAdmin(user: User | null): boolean | null; protected userIsAdmin(user: any): any;
} }
import Modal from "./Modal";
import Stream from "../utils/Stream";
import ItemList from "../utils/ItemList";

View File

@@ -16,10 +16,10 @@ export default class LinkButton extends Button<import("./Button").IButtonAttrs>
/** /**
* Determine whether a component with the given attrs is 'active'. * Determine whether a component with the given attrs is 'active'.
* *
* @param {object} attrs * @param {Object} attrs
* @return {boolean} * @return {Boolean}
*/ */
static isActive(attrs: object): boolean; static isActive(attrs: Object): boolean;
constructor(); constructor();
} }
import Button from "./Button"; import Button from "./Button";

View File

@@ -22,8 +22,8 @@ export default abstract class Modal<ModalAttrs extends IInternalModalAttrs = IIn
/** /**
* Attributes for an alert component to show below the header. * Attributes for an alert component to show below the header.
*/ */
alertAttrs: AlertAttrs | null; alertAttrs: AlertAttrs;
oninit(vnode: Mithril.Vnode<ModalAttrs, this>): void; oninit(vnode: Mithril.VnodeDOM<ModalAttrs, this>): void;
oncreate(vnode: Mithril.VnodeDOM<ModalAttrs, this>): void; oncreate(vnode: Mithril.VnodeDOM<ModalAttrs, this>): void;
onbeforeremove(vnode: Mithril.VnodeDOM<ModalAttrs, this>): Promise<void> | void; onbeforeremove(vnode: Mithril.VnodeDOM<ModalAttrs, this>): Promise<void> | void;
/** /**
@@ -37,7 +37,7 @@ export default abstract class Modal<ModalAttrs extends IInternalModalAttrs = IIn
/** /**
* Get the title of the modal dialog. * Get the title of the modal dialog.
*/ */
abstract title(): Mithril.Children; abstract title(): string;
/** /**
* Get the content of the modal. * Get the content of the modal.
*/ */

View File

@@ -18,23 +18,23 @@ export default class Navigation extends Component<import("../Component").Compone
/** /**
* Get the back button. * Get the back button.
* *
* @return {import('mithril').Children} * @return {Object}
* @protected * @protected
*/ */
protected getBackButton(): import('mithril').Children; protected getBackButton(): Object;
/** /**
* Get the pane pinned toggle button. * Get the pane pinned toggle button.
* *
* @return {import('mithril').Children} * @return {Object|String}
* @protected * @protected
*/ */
protected getPaneButton(): import('mithril').Children; protected getPaneButton(): Object | string;
/** /**
* Get the drawer toggle button. * Get the drawer toggle button.
* *
* @return {import('mithril').Children} * @return {Object|String}
* @protected * @protected
*/ */
protected getDrawerButton(): import('mithril').Children; protected getDrawerButton(): Object | string;
} }
import Component from "../Component"; import Component from "../Component";

View File

@@ -1,12 +1,4 @@
/// <reference types="mithril" /> export default class RequestErrorModal extends Modal<import("./Modal").IInternalModalAttrs> {
import type RequestError from '../utils/RequestError'; constructor();
import Modal, { IInternalModalAttrs } from './Modal';
export interface IRequestErrorModalAttrs extends IInternalModalAttrs {
error: RequestError;
formattedError: string[];
}
export default class RequestErrorModal<CustomAttrs extends IRequestErrorModalAttrs = IRequestErrorModalAttrs> extends Modal<CustomAttrs> {
className(): string;
title(): string;
content(): JSX.Element;
} }
import Modal from "./Modal";

View File

@@ -7,10 +7,9 @@ export default class SplitDropdown extends Dropdown {
* Get the first child. If the first child is an array, the first item in that * Get the first child. If the first child is an array, the first item in that
* array will be returned. * array will be returned.
* *
* @param {unknown[] | unknown} children * @return {*}
* @return {unknown}
* @protected * @protected
*/ */
protected getFirstChild(children: unknown[] | unknown): unknown; protected getFirstChild(children: any): any;
} }
import Dropdown from "./Dropdown"; import Dropdown from "./Dropdown";

View File

@@ -36,19 +36,19 @@ export default class TextEditor extends Component<import("../Component").Compone
/** /**
* Build an item list for the text editor controls. * Build an item list for the text editor controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
controlItems(): ItemList<import('mithril').Children>; controlItems(): ItemList<any>;
/** /**
* Build an item list for the toolbar controls. * Build an item list for the toolbar controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
toolbarItems(): ItemList<import('mithril').Children>; toolbarItems(): ItemList<any>;
/** /**
* Handle input into the textarea. * Handle input into the textarea.
* *
* @param {string} value * @param {String} value
*/ */
oninput(value: string): void; oninput(value: string): void;
/** /**

View File

@@ -23,7 +23,7 @@
* @param methods The name or names of the method(s) to extend * @param methods The name or names of the method(s) to extend
* @param callback A callback which mutates the method's output * @param callback A callback which mutates the method's output
*/ */
export declare function extend<T extends Record<string, any>, K extends KeyOfType<T, Function>>(object: T, methods: K | K[], callback: (this: T, val: ReturnType<T[K]>, ...args: Parameters<T[K]>) => void): void; export declare function extend<T extends object, K extends KeyOfType<T, Function>>(object: T, methods: K | K[], callback: (this: T, val: ReturnType<T[K]>, ...args: Parameters<T[K]>) => void): void;
/** /**
* Override an object's method by replacing it with a new function, so that the * Override an object's method by replacing it with a new function, so that the
* new function will be run every time the object's method is called. * new function will be run every time the object's method is called.
@@ -51,4 +51,4 @@ export declare function extend<T extends Record<string, any>, K extends KeyOfTyp
* @param methods The name or names of the method(s) to override * @param methods The name or names of the method(s) to override
* @param newMethod The method to replace it with * @param newMethod The method to replace it with
*/ */
export declare function override<T extends Record<any, any>, K extends KeyOfType<T, Function>>(object: T, methods: K | K[], newMethod: (this: T, orig: T[K], ...args: Parameters<T[K]>) => void): void; export declare function override<T extends object, K extends KeyOfType<T, Function>>(object: T, methods: K | K[], newMethod: (this: T, orig: T[K], ...args: Parameters<T[K]>) => void): void;

View File

@@ -10,17 +10,3 @@
* can fix. * can fix.
*/ */
export default function fireDebugWarning(...args: Parameters<typeof console.warn>): void; export default function fireDebugWarning(...args: Parameters<typeof console.warn>): void;
/**
* Fire a Flarum deprecation warning which is shown in the JS console.
*
* These warnings are only shown when the forum is in debug mode, and the function exists to
* reduce bundle size caused by multiple warnings across our JavaScript.
*
* @param message The message to display. (Short, but sweet, please!)
* @param githubId The PR or Issue ID with more info in relation to this change.
* @param [removedFrom] The version in which this feature will be completely removed. (default: 2.0)
* @param [repo] The repo which the issue or PR is located in. (default: flarum/core)
*
* @see {@link fireDebugWarning}
*/
export declare function fireDeprecationWarning(message: string, githubId: string, removedFrom?: string, repo?: string): void;

View File

@@ -1,27 +1,16 @@
import type Mithril from 'mithril'; import type Mithril from 'mithril';
import { ComponentAttrs } from '../Component'; import Component, { ComponentAttrs } from '../Component';
declare type ModdedVnodeAttrs = { export interface ModdedVnodeAttrs {
itemClassName?: string; itemClassName?: string;
key?: string; key?: string;
}; }
declare type ModdedTag = Mithril.Vnode['tag'] & { export declare type ModdedVnode<Attrs> = Mithril.Vnode<ModdedVnodeAttrs, Component<Attrs> | {}> & {
isListItem?: boolean;
isActive?: (attrs: ComponentAttrs) => boolean;
};
declare type ModdedVnode = Mithril.Vnode<ModdedVnodeAttrs> & {
itemName?: string; itemName?: string;
itemClassName?: string; itemClassName?: string;
tag: ModdedTag; tag: Mithril.Vnode['tag'] & {
}; isListItem?: boolean;
declare type ModdedChild = ModdedVnode | string | number | boolean | null | undefined; isActive?: (attrs: ComponentAttrs) => boolean;
declare type ModdedChildArray = ModdedChildren[]; };
declare type ModdedChildren = ModdedChild | ModdedChildArray;
/**
* This type represents an element of a list returned by `ItemList.toArray()`,
* coupled with some static properties used on various components.
*/
export declare type ModdedChildrenWithItemName = ModdedChildren & {
itemName?: string;
}; };
/** /**
* The `listItems` helper wraps an array of components in the provided tag, * The `listItems` helper wraps an array of components in the provided tag,
@@ -30,5 +19,4 @@ export declare type ModdedChildrenWithItemName = ModdedChildren & {
* By default, this tag is an `<li>` tag, but this is customisable through the * By default, this tag is an `<li>` tag, but this is customisable through the
* second function parameter, `customTag`. * second function parameter, `customTag`.
*/ */
export default function listItems<Attrs extends ComponentAttrs>(rawItems: ModdedChildrenWithItemName[], customTag?: VnodeElementTag<Attrs>, attributes?: Attrs): Mithril.Vnode[]; export default function listItems<Attrs extends Record<string, unknown>>(rawItems: ModdedVnode<Attrs> | ModdedVnode<Attrs>[], customTag?: string | Component<Attrs>, attributes?: Attrs): Mithril.Vnode[];
export {};

View File

@@ -6,7 +6,7 @@
* punctuateSeries(['Toby', 'Franz', 'Dominion']) // Toby, Franz, and Dominion * punctuateSeries(['Toby', 'Franz', 'Dominion']) // Toby, Franz, and Dominion
* ``` * ```
* *
* @param {import('mithril').Children[]} items * @param {Array} items
* @return {import('mithril').Children}')} * @return {VirtualElement}
*/ */
export default function punctuateSeries(items: import('mithril').Children[]): import('mithril').Children; export default function punctuateSeries(items: any[]): any;

View File

@@ -4,4 +4,4 @@ import User from '../models/User';
* The `username` helper displays a user's username in a <span class="username"> * The `username` helper displays a user's username in a <span class="username">
* tag. If the user doesn't exist, the username will be displayed as [deleted]. * tag. If the user doesn't exist, the username will be displayed as [deleted].
*/ */
export default function username(user: User | null | undefined | false): Mithril.Vnode; export default function username(user: User): Mithril.Vnode;

View File

@@ -1,48 +1,3 @@
import Model from '../Model';
import ItemList from '../utils/ItemList';
import Mithril from 'mithril';
import Post from './Post';
import User from './User';
export default class Discussion extends Model { export default class Discussion extends Model {
title(): string;
slug(): string;
createdAt(): Date | undefined;
user(): false | User | null;
firstPost(): false | Post | null;
lastPostedAt(): Date | null | undefined;
lastPostedUser(): false | User | null;
lastPost(): false | Post | null;
lastPostNumber(): number | null | undefined;
commentCount(): number | undefined;
replyCount(): Number;
posts(): false | (Post | undefined)[];
mostRelevantPost(): false | Post | null;
lastReadAt(): Date | null | undefined;
lastReadPostNumber(): number | null | undefined;
isUnread(): boolean;
isRead(): boolean;
hiddenAt(): Date | null | undefined;
hiddenUser(): false | User | null;
isHidden(): boolean;
canReply(): boolean | undefined;
canRename(): boolean | undefined;
canHide(): boolean | undefined;
canDelete(): boolean | undefined;
/**
* Remove a post from the discussion's posts relationship.
*/
removePost(id: string): void;
/**
* Get the estimated number of unread posts in this discussion for the current
* user.
*/
unreadCount(): number;
/**
* Get the Badge components that apply to this discussion.
*/
badges(): ItemList<Mithril.Children>;
/**
* Get a list of all of the post IDs in this discussion.
*/
postIds(): string[];
} }
import Model from "../Model";

View File

@@ -1,4 +1,3 @@
import Model from '../Model';
export default class Forum extends Model { export default class Forum extends Model {
apiEndpoint(): string;
} }
import Model from "../Model";

View File

@@ -1,11 +1,9 @@
import Model from '../Model'; export default Group;
export default class Group extends Model { declare class Group extends Model {
static ADMINISTRATOR_ID: string;
static GUEST_ID: string;
static MEMBER_ID: string;
nameSingular(): string;
namePlural(): string;
color(): string | null;
icon(): string | null;
isHidden(): boolean;
} }
declare namespace Group {
const ADMINISTRATOR_ID: string;
const GUEST_ID: string;
const MEMBER_ID: string;
}
import Model from "../Model";

View File

@@ -1,11 +1,3 @@
import Model from '../Model';
import User from './User';
export default class Notification extends Model { export default class Notification extends Model {
contentType(): string;
content(): string;
createdAt(): Date;
isRead(): boolean;
user(): false | User;
fromUser(): false | User | null;
subject(): false | Model | null;
} }
import Model from "../Model";

View File

@@ -1,23 +1,3 @@
import Model from '../Model';
import Discussion from './Discussion';
import User from './User';
export default class Post extends Model { export default class Post extends Model {
number(): number;
discussion(): Discussion;
createdAt(): Date;
user(): false | User;
contentType(): string | null;
content(): string | null | undefined;
contentHtml(): string | null | undefined;
renderFailed(): boolean | undefined;
contentPlain(): string | null | undefined;
editedAt(): Date | null | undefined;
editedUser(): false | User | null;
isEdited(): boolean;
hiddenAt(): Date | null | undefined;
hiddenUser(): false | User | null;
isHidden(): boolean;
canEdit(): boolean | undefined;
canHide(): boolean | undefined;
canDelete(): boolean | undefined;
} }
import Model from "../Model";

View File

@@ -1,46 +1,3 @@
import { Color } from 'color-thief-browser';
import Model from '../Model';
import ItemList from '../utils/ItemList';
import Mithril from 'mithril';
import Group from './Group';
export default class User extends Model { export default class User extends Model {
username(): string;
slug(): string;
displayName(): string;
email(): string | undefined;
isEmailConfirmed(): boolean | undefined;
password(): string | undefined;
avatarUrl(): string | null;
preferences(): Record<string, any> | null | undefined;
groups(): false | (Group | undefined)[];
joinTime(): Date | null | undefined;
lastSeenAt(): Date | null | undefined;
markedAllAsReadAt(): Date | null | undefined;
unreadNotificationCount(): number | undefined;
newNotificationCount(): number | undefined;
discussionCount(): number | undefined;
commentCount(): number | undefined;
canEdit(): boolean | undefined;
canEditCredentials(): boolean | undefined;
canEditGroups(): boolean | undefined;
canDelete(): boolean | undefined;
color(): string;
protected avatarColor: Color | null;
/**
* Check whether or not the user has been seen in the last 5 minutes.
*/
isOnline(): boolean;
/**
* Get the Badge components that apply to this user.
*/
badges(): ItemList<Mithril.Children>;
/**
* Calculate the dominant color of the user's avatar. The dominant color will
* be set to the `avatarColor` property once it has been calculated.
*/
protected calculateAvatarColor(): void;
/**
* Update the user's preferences.
*/
savePreferences(newPreferences: Record<string, unknown>): Promise<this>;
} }
import Model from "../Model";

View File

@@ -20,11 +20,11 @@ export default class AlertManagerState {
/** /**
* Show an Alert in the alerts area. * Show an Alert in the alerts area.
* *
* @return The alert's ID, which can be used to dismiss the alert. * @returns The alert's ID, which can be used to dismiss the alert.
*/ */
show(children: Mithril.Children): AlertIdentifier; show(children: Mithril.Children): AlertIdentifier;
show(attrs: AlertAttrs, children: Mithril.Children): AlertIdentifier; show(attrs: AlertAttrs, children: Mithril.Children): AlertIdentifier;
show(componentClass: typeof Alert, attrs: AlertAttrs, children: Mithril.Children): AlertIdentifier; show(componentClass: Alert, attrs: AlertAttrs, children: Mithril.Children): AlertIdentifier;
/** /**
* Dismiss an alert. * Dismiss an alert.
*/ */

View File

@@ -1,16 +1,4 @@
import type Component from '../Component';
import Modal from '../components/Modal'; import Modal from '../components/Modal';
/**
* Ideally, `show` would take a higher-kinded generic, ala:
* `show<Attrs, C>(componentClass: C<Attrs>, attrs: Attrs): void`
* Unfortunately, TypeScript does not support this:
* https://github.com/Microsoft/TypeScript/issues/1213
* Therefore, we have to use this ugly, messy workaround.
*/
declare type UnsafeModalClass = ComponentClass<any, Modal> & {
isDismissible: boolean;
component: typeof Component.component;
};
/** /**
* Class used to manage modal state. * Class used to manage modal state.
* *
@@ -21,15 +9,9 @@ export default class ModalManagerState {
* @internal * @internal
*/ */
modal: null | { modal: null | {
componentClass: UnsafeModalClass; componentClass: typeof Modal;
attrs?: Record<string, unknown>; attrs?: Record<string, unknown>;
key: number;
}; };
/**
* Used to force re-initialization of modals if a modal
* is replaced by another of the same type.
*/
private key;
private closeTimeout?; private closeTimeout?;
/** /**
* Shows a modal dialog. * Shows a modal dialog.
@@ -43,7 +25,7 @@ export default class ModalManagerState {
* // This "hack" is needed due to quirks with nested redraws in Mithril. * // This "hack" is needed due to quirks with nested redraws in Mithril.
* setTimeout(() => app.modal.show(MyCoolModal, { attr: 'value' }), 0); * setTimeout(() => app.modal.show(MyCoolModal, { attr: 'value' }), 0);
*/ */
show(componentClass: UnsafeModalClass, attrs?: Record<string, unknown>): void; show(componentClass: typeof Modal, attrs?: Record<string, unknown>): void;
/** /**
* Closes the currently open dialog, if one is open. * Closes the currently open dialog, if one is open.
*/ */
@@ -51,8 +33,7 @@ export default class ModalManagerState {
/** /**
* Checks if a modal is currently open. * Checks if a modal is currently open.
* *
* @return `true` if a modal dialog is currently open, otherwise `false`. * @returns `true` if a modal dialog is currently open, otherwise `false`.
*/ */
isModalOpen(): boolean; isModalOpen(): boolean;
} }
export {};

View File

@@ -5,11 +5,12 @@ export default class PageState {
/** /**
* Determine whether the page matches the given class and data. * Determine whether the page matches the given class and data.
* *
* @param {object} type The page class to check against. Subclasses are accepted as well. * @param {object} type The page class to check against. Subclasses are
* @param {Record<string, unknown>} data * accepted as well.
* @param {object} data
* @return {boolean} * @return {boolean}
*/ */
matches(type: object, data?: Record<string, unknown>): boolean; matches(type: object, data?: object): boolean;
get(key: any): any; get(key: any): any;
set(key: any, value: any): void; set(key: any, value: any): void;
} }

View File

@@ -1,5 +1,4 @@
import Model from '../Model'; import Model from '../Model';
import { ApiQueryParamsPlural, ApiResponsePlural } from '../Store';
export interface Page<TModel> { export interface Page<TModel> {
number: number; number: number;
items: TModel[]; items: TModel[];
@@ -14,9 +13,6 @@ export interface PaginationLocation {
export interface PaginatedListParams { export interface PaginatedListParams {
[key: string]: any; [key: string]: any;
} }
export interface PaginatedListRequestParams extends Omit<ApiQueryParamsPlural, 'include'> {
include?: string | string[];
}
export default abstract class PaginatedListState<T extends Model, P extends PaginatedListParams = PaginatedListParams> { export default abstract class PaginatedListState<T extends Model, P extends PaginatedListParams = PaginatedListParams> {
protected location: PaginationLocation; protected location: PaginationLocation;
protected pageSize: number; protected pageSize: number;
@@ -30,11 +26,11 @@ export default abstract class PaginatedListState<T extends Model, P extends Pagi
clear(): void; clear(): void;
loadPrev(): Promise<void>; loadPrev(): Promise<void>;
loadNext(): Promise<void>; loadNext(): Promise<void>;
protected parseResults(pg: number, results: ApiResponsePlural<T>): void; protected parseResults(pg: number, results: T[]): void;
/** /**
* Load a new page of results. * Load a new page of results.
*/ */
protected loadPage(page?: number): Promise<ApiResponsePlural<T>>; protected loadPage(page?: number): Promise<T[]>;
/** /**
* Get the parameters that should be passed in the API request. * Get the parameters that should be passed in the API request.
* Do not include page offset unless subclass overrides loadPage. * Do not include page offset unless subclass overrides loadPage.
@@ -42,7 +38,7 @@ export default abstract class PaginatedListState<T extends Model, P extends Pagi
* @abstract * @abstract
* @see loadPage * @see loadPage
*/ */
protected requestParams(): PaginatedListRequestParams; protected requestParams(): any;
/** /**
* Update the `this.params` object, calling `refresh` if they have changed. * Update the `this.params` object, calling `refresh` if they have changed.
* Use `requestParams` for converting `this.params` into API parameters * Use `requestParams` for converting `this.params` into API parameters
@@ -77,7 +73,7 @@ export default abstract class PaginatedListState<T extends Model, P extends Pagi
/** /**
* Stored state parameters. * Stored state parameters.
*/ */
getParams(): P; getParams(): any;
protected getNextPageNumber(): number; protected getNextPageNumber(): number;
protected getPrevPageNumber(): number; protected getPrevPageNumber(): number;
protected paramsChanged(newParams: P): boolean; protected paramsChanged(newParams: P): boolean;

View File

@@ -34,15 +34,20 @@ export default class Drawer {
* Check whether or not the drawer is currently open. * Check whether or not the drawer is currently open.
* *
* @return {boolean} * @return {boolean}
* @public
*/ */
isOpen(): boolean; public isOpen(): boolean;
/** /**
* Hide the drawer. * Hide the drawer.
*
* @public
*/ */
hide(): void; public hide(): void;
/** /**
* Show the drawer. * Show the drawer.
*
* @public
*/ */
show(): void; public show(): void;
$backdrop: JQuery<HTMLElement> | undefined; $backdrop: JQuery<HTMLElement> | undefined;
} }

View File

@@ -192,7 +192,7 @@ export default class ItemList<T> {
* *
* @param content The item's content (objects only) * @param content The item's content (objects only)
* @param key The item's key * @param key The item's key
* @return Proxied content * @returns Proxied content
* *
* @internal * @internal
*/ */

View File

@@ -1,6 +1,6 @@
import type Mithril from 'mithril'; import type Mithril from 'mithril';
import type { AlertAttrs } from '../components/Alert';
export declare type InternalFlarumRequestOptions<ResponseType> = Mithril.RequestOptions<ResponseType> & { export declare type InternalFlarumRequestOptions<ResponseType> = Mithril.RequestOptions<ResponseType> & {
errorHandler: (error: RequestError) => void;
url: string; url: string;
}; };
export default class RequestError<ResponseType = string> { export default class RequestError<ResponseType = string> {
@@ -16,6 +16,6 @@ export default class RequestError<ResponseType = string> {
[key: string]: unknown; [key: string]: unknown;
}[]; }[];
} | null; } | null;
alert: AlertAttrs | null; alert: any;
constructor(status: number, responseText: string | null, options: InternalFlarumRequestOptions<ResponseType>, xhr: XMLHttpRequest); constructor(status: number, responseText: string | null, options: InternalFlarumRequestOptions<ResponseType>, xhr: XMLHttpRequest);
} }

View File

@@ -6,6 +6,7 @@ export default class ScrollListener {
/** /**
* @param {(top: number) => void} callback The callback to run when the scroll position * @param {(top: number) => void} callback The callback to run when the scroll position
* changes. * changes.
* @public
*/ */
constructor(callback: (top: number) => void); constructor(callback: (top: number) => void);
callback: (top: number) => void; callback: (top: number) => void;
@@ -19,15 +20,21 @@ export default class ScrollListener {
protected loop(): void; protected loop(): void;
/** /**
* Run the callback, whether there was a scroll event or not. * Run the callback, whether there was a scroll event or not.
*
* @public
*/ */
update(): void; public update(): void;
/** /**
* Start listening to and handling the window's scroll position. * Start listening to and handling the window's scroll position.
*
* @public
*/ */
start(): void; public start(): void;
active: (() => void) | null | undefined; active: (() => void) | null | undefined;
/** /**
* Stop listening to and handling the window's scroll position. * Stop listening to and handling the window's scroll position.
*
* @public
*/ */
stop(): void; public stop(): void;
} }

View File

@@ -8,7 +8,7 @@
* position can be anchor to an element that is in or below the viewport, so * position can be anchor to an element that is in or below the viewport, so
* the content in the viewport will stay the same. * the content in the viewport will stay the same.
* *
* @param {HTMLElement | SVGElement | Element} element The element to anchor the scroll position to. * @param {DOMElement} element The element to anchor the scroll position to.
* @param {() => void} callback The callback to run that will change page content. * @param {Function} callback The callback to run that will change page content.
*/ */
export default function anchorScroll(element: HTMLElement | SVGElement | Element, callback: () => void): void; export default function anchorScroll(element: any, callback: Function): void;

View File

@@ -1,10 +1,10 @@
import Model from '../Model';
/** /**
* The `computed` utility creates a function that will cache its output until * The `computed` utility creates a function that will cache its output until
* any of the dependent values are dirty. * any of the dependent values are dirty.
* *
* @param dependentKeys The keys of the dependent values. * @param {...String} dependentKeys The keys of the dependent values.
* @param compute The function which computes the value using the * @param {function} compute The function which computes the value using the
* dependent values. * dependent values.
* @return {Function}
*/ */
export default function computed<T, M = Model>(...args: [...string[], (this: M, ...args: unknown[]) => T]): () => T; export default function computed(...dependentKeys: string[]): Function;

View File

@@ -1,97 +1,79 @@
declare namespace _default { declare namespace _default {
const handlers: Record<string, unknown>; const handlers: Object;
/** /**
* Get all of the registered handlers for an event. * Get all of the registered handlers for an event.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @return {Function[]} * @return {Array}
* @protected * @protected
*
* @deprecated
*/ */
function getHandlers(event: string): Function[]; function getHandlers(event: string): any[];
/** /**
* Get all of the registered handlers for an event. * Get all of the registered handlers for an event.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @return {Function[]} * @return {Array}
* @protected * @protected
*
* @deprecated
*/ */
function getHandlers(event: string): Function[]; function getHandlers(event: string): any[];
/** /**
* Trigger an event. * Trigger an event.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {any[]} args Arguments to pass to event handlers. * @param {...*} args Arguments to pass to event handlers.
* * @public
* @deprecated
*/ */
function trigger(event: string, ...args: any[]): void; function trigger(event: string, ...args: any[]): void;
/** /**
* Trigger an event. * Trigger an event.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {any[]} args Arguments to pass to event handlers. * @param {...*} args Arguments to pass to event handlers.
* * @public
* @deprecated
*/ */
function trigger(event: string, ...args: any[]): void; function trigger(event: string, ...args: any[]): void;
/** /**
* Register an event handler. * Register an event handler.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function to handle the event. * @param {function} handler The function to handle the event.
*
* @deprecated
*/ */
function on(event: string, handler: Function): void; function on(event: string, handler: Function): void;
/** /**
* Register an event handler. * Register an event handler.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function to handle the event. * @param {function} handler The function to handle the event.
*
* @deprecated
*/ */
function on(event: string, handler: Function): void; function on(event: string, handler: Function): void;
/** /**
* Register an event handler so that it will run only once, and then * Register an event handler so that it will run only once, and then
* unregister itself. * unregister itself.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function to handle the event. * @param {function} handler The function to handle the event.
*
* @deprecated
*/ */
function one(event: string, handler: Function): void; function one(event: string, handler: Function): void;
/** /**
* Register an event handler so that it will run only once, and then * Register an event handler so that it will run only once, and then
* unregister itself. * unregister itself.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function to handle the event. * @param {function} handler The function to handle the event.
*
* @deprecated
*/ */
function one(event: string, handler: Function): void; function one(event: string, handler: Function): void;
/** /**
* Unregister an event handler. * Unregister an event handler.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function that handles the event. * @param {function} handler The function that handles the event.
*
* @deprecated
*/ */
function off(event: string, handler: Function): void; function off(event: string, handler: Function): void;
/** /**
* Unregister an event handler. * Unregister an event handler.
* *
* @param {string} event The name of the event. * @param {String} event The name of the event.
* @param {Function} handler The function that handles the event. * @param {function} handler The function that handles the event.
*
* @deprecated
*/ */
function off(event: string, handler: Function): void; function off(event: string, handler: Function): void;
} }

View File

@@ -5,8 +5,8 @@
* @example * @example
* class MyClass extends mixin(ExistingClass, evented, etc) {} * class MyClass extends mixin(ExistingClass, evented, etc) {}
* *
* @param {object} Parent The class to extend the new class from. * @param {Class} Parent The class to extend the new class from.
* @param {Record<string, any>[]} mixins The objects to mix in. * @param {...Object} mixins The objects to mix in.
* @return {object} A new class that extends Parent and contains the mixins. * @return {Class} A new class that extends Parent and contains the mixins.
*/ */
export default function mixin(Parent: object, ...mixins: Record<string, any>[]): object; export default function mixin(Parent: any, ...mixins: Object[]): any;

View File

@@ -9,7 +9,6 @@ interface StyleArgs {
scanFor: string; scanFor: string;
surroundWithNewlines: boolean; surroundWithNewlines: boolean;
orderedList: boolean; orderedList: boolean;
unorderedList: boolean;
trimFirst: boolean; trimFirst: boolean;
} }
export default function styleSelectedText(textarea: HTMLTextAreaElement, styleArgs: StyleArgs): void; export default function styleSelectedText(textarea: HTMLTextAreaElement, styleArgs: StyleArgs): void;

View File

@@ -4,8 +4,8 @@ declare var _default: {
Store: typeof import("../common/Store").default; Store: typeof import("../common/Store").default;
'utils/BasicEditorDriver': typeof BasicEditorDriver; 'utils/BasicEditorDriver': typeof BasicEditorDriver;
'utils/evented': { 'utils/evented': {
handlers: Record<string, unknown>; handlers: Object;
getHandlers(event: string): Function[]; getHandlers(event: string): any[];
trigger(event: string, ...args: any[]): void; trigger(event: string, ...args: any[]): void;
on(event: string, handler: Function): void; on(event: string, handler: Function): void;
one(event: string, handler: Function): void; one(event: string, handler: Function): void;
@@ -92,38 +92,38 @@ declare var _default: {
'states/PaginatedListState': typeof import("../common/states/PaginatedListState").default; 'states/PaginatedListState': typeof import("../common/states/PaginatedListState").default;
} & { } & {
'utils/PostControls': { 'utils/PostControls': {
controls(post: import("../common/models/Post").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; controls(post: any, context: any): import("../common/utils/ItemList").default<any>;
userControls(post: import("../common/models/Post").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; userControls(post: any, context: any): import("../common/utils/ItemList").default<any>;
moderationControls(post: import("../common/models/Post").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; moderationControls(post: any, context: any): import("../common/utils/ItemList").default<any>;
destructiveControls(post: import("../common/models/Post").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; destructiveControls(post: any, context: any): import("../common/utils/ItemList").default<any>;
editAction(): Promise<void>; editAction(): Promise<any>;
hideAction(): Promise<void>; hideAction(): Promise<any>;
restoreAction(): Promise<void>; restoreAction(): Promise<any>;
deleteAction(context: any): Promise<void>; deleteAction(context: any): Promise<any>;
}; };
'utils/KeyboardNavigatable': typeof KeyboardNavigatable; 'utils/KeyboardNavigatable': typeof KeyboardNavigatable;
'utils/slidable': typeof slidable; 'utils/slidable': typeof slidable;
'utils/History': typeof History; 'utils/History': typeof History;
'utils/DiscussionControls': { 'utils/DiscussionControls': {
controls(discussion: import("../common/models/Discussion").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; controls(discussion: any, context: any): import("../common/utils/ItemList").default<any>;
userControls(discussion: import("../common/models/Discussion").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; userControls(discussion: any, context: any): import("../common/utils/ItemList").default<any>;
moderationControls(discussion: import("../common/models/Discussion").default): import("../common/utils/ItemList").default<import("mithril").Children>; moderationControls(discussion: any): import("../common/utils/ItemList").default<any>;
destructiveControls(discussion: import("../common/models/Discussion").default): import("../common/utils/ItemList").default<import("mithril").Children>; destructiveControls(discussion: any): import("../common/utils/ItemList").default<any>;
replyAction(goToLast: boolean, forceRefresh: boolean): Promise<void>; replyAction(goToLast: boolean, forceRefresh: boolean): Promise<any>;
hideAction(): Promise<void>; hideAction(): Promise<any>;
restoreAction(): Promise<void>; restoreAction(): Promise<any>;
deleteAction(): Promise<void>; deleteAction(): Promise<any>;
renameAction(): any; renameAction(): Promise<any>;
}; };
'utils/alertEmailConfirmation': typeof alertEmailConfirmation; 'utils/alertEmailConfirmation': typeof alertEmailConfirmation;
'utils/UserControls': { 'utils/UserControls': {
controls(user: import("../common/models/User").default, context: import("../common/Component").default<any, any>): import("../common/utils/ItemList").default<import("mithril").Children>; controls(user: any, context: any): import("../common/utils/ItemList").default<any>;
userControls(): import("../common/utils/ItemList").default<import("mithril").Children>; userControls(): import("../common/utils/ItemList").default<any>;
moderationControls(user: import("../common/models/User").default): import("../common/utils/ItemList").default<import("mithril").Children>; moderationControls(user: any): import("../common/utils/ItemList").default<any>;
destructiveControls(user: import("../common/models/User").default): import("../common/utils/ItemList").default<import("mithril").Children>; destructiveControls(user: any): import("../common/utils/ItemList").default<any>;
deleteAction(user: import("../common/models/User").default): void; deleteAction(user: any): void;
showDeletionAlert(user: import("../common/models/User").default, type: string): void; showDeletionAlert(user: any, type: string): void;
editAction(user: import("../common/models/User").default): void; editAction(user: any): void;
}; };
'utils/Pane': typeof Pane; 'utils/Pane': typeof Pane;
'utils/BasicEditorDriver': typeof BasicEditorDriver; 'utils/BasicEditorDriver': typeof BasicEditorDriver;

View File

@@ -24,36 +24,36 @@ export default class AvatarEditor extends Component<import("../../common/Compone
/** /**
* Get the items in the edit avatar dropdown menu. * Get the items in the edit avatar dropdown menu.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
controlItems(): ItemList<import('mithril').Children>; controlItems(): ItemList<any>;
/** /**
* Enable dragover style * Enable dragover style
* *
* @param {DragEvent} e * @param {Event} e
*/ */
enableDragover(e: DragEvent): void; enableDragover(e: Event): void;
/** /**
* Disable dragover style * Disable dragover style
* *
* @param {DragEvent} e * @param {Event} e
*/ */
disableDragover(e: DragEvent): void; disableDragover(e: Event): void;
/** /**
* Upload avatar when file is dropped into dropzone. * Upload avatar when file is dropped into dropzone.
* *
* @param {DragEvent} e * @param {Event} e
*/ */
dropUpload(e: DragEvent): void; dropUpload(e: Event): void;
/** /**
* If the user doesn't have an avatar, there's no point in showing the * If the user doesn't have an avatar, there's no point in showing the
* controls dropdown, because only one option would be viable: uploading. * controls dropdown, because only one option would be viable: uploading.
* Thus, when the avatar editor's dropdown toggle button is clicked, we prompt * Thus, when the avatar editor's dropdown toggle button is clicked, we prompt
* the user to upload an avatar immediately. * the user to upload an avatar immediately.
* *
* @param {MouseEvent} e * @param {Event} e
*/ */
quickUpload(e: MouseEvent): void; quickUpload(e: Event): void;
/** /**
* Upload avatar using file picker * Upload avatar using file picker
*/ */
@@ -72,17 +72,17 @@ export default class AvatarEditor extends Component<import("../../common/Compone
* After a successful upload/removal, push the updated user data into the * After a successful upload/removal, push the updated user data into the
* store, and force a recomputation of the user's avatar color. * store, and force a recomputation of the user's avatar color.
* *
* @param {object} response * @param {Object} response
* @protected * @protected
*/ */
protected success(response: object): void; protected success(response: Object): void;
/** /**
* If avatar upload/removal fails, stop loading. * If avatar upload/removal fails, stop loading.
* *
* @param {object} response * @param {Object} response
* @protected * @protected
*/ */
protected failure(response: object): void; protected failure(response: Object): void;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -32,9 +32,9 @@ export default class CommentPost extends Post {
/** /**
* Build an item list for the post's header. * Build an item list for the post's header.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
headerItems(): ItemList<import('mithril').Children>; headerItems(): ItemList<any>;
} }
import Post from "./Post"; import Post from "./Post";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -21,9 +21,9 @@ export default class Composer extends Component<import("../../common/Component")
/** /**
* Resize the composer according to mouse movement. * Resize the composer according to mouse movement.
* *
* @param {MouseEvent} e * @param {Event} e
*/ */
onmousemove(e: MouseEvent): void; onmousemove(e: Event): void;
/** /**
* Finish resizing the composer when the mouse is released. * Finish resizing the composer when the mouse is released.
*/ */
@@ -83,23 +83,23 @@ export default class Composer extends Component<import("../../common/Component")
/** /**
* Build an item list for the composer's controls. * Build an item list for the composer's controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
controlItems(): ItemList<import('mithril').Children>; controlItems(): ItemList<any>;
/** /**
* Initialize default Composer height. * Initialize default Composer height.
*/ */
initializeHeight(): void; initializeHeight(): void;
/** /**
* Default height of the Composer in case none is saved. * Default height of the Composer in case none is saved.
* @returns {number} * @returns {Integer}
*/ */
defaultHeight(): number; defaultHeight(): any;
/** /**
* Save a new Composer height and update the DOM. * Save a new Composer height and update the DOM.
* @param {number} height * @param {Integer} height
*/ */
changeHeight(height: number): void; changeHeight(height: any): void;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -27,15 +27,15 @@ export default class ComposerBody extends Component<import("../../common/Compone
/** /**
* Check if there is any unsaved data. * Check if there is any unsaved data.
* *
* @return {boolean} * @return {String}
*/ */
hasChanges(): boolean; hasChanges(): string;
/** /**
* Build an item list for the composer's header. * Build an item list for the composer's header.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
headerItems(): ItemList<import('mithril').Children>; headerItems(): ItemList<any>;
/** /**
* Handle the submit event of the text editor. * Handle the submit event of the text editor.
* *

View File

@@ -21,14 +21,14 @@ export default class DiscussionComposer extends ComposerBody {
* Handle the title input's keydown event. When the return key is pressed, * Handle the title input's keydown event. When the return key is pressed,
* move the focus to the start of the text editor. * move the focus to the start of the text editor.
* *
* @param {KeyboardEvent} e * @param {Event} e
*/ */
onkeydown(e: KeyboardEvent): void; onkeydown(e: Event): void;
/** /**
* Get the data to submit to the server when the discussion is saved. * Get the data to submit to the server when the discussion is saved.
* *
* @return {Record<string, unknown>} * @return {Object}
*/ */
data(): Record<string, unknown>; data(): Object;
} }
import ComposerBody from "./ComposerBody"; import ComposerBody from "./ComposerBody";

View File

@@ -10,9 +10,9 @@ export default class DiscussionHero extends Component<import("../../common/Compo
/** /**
* Build an item list for the contents of the discussion hero. * Build an item list for the contents of the discussion hero.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -23,7 +23,7 @@ export default class DiscussionListItem extends Component<import("../../common/C
/** /**
* Determine whether or not the discussion is currently being viewed. * Determine whether or not the discussion is currently being viewed.
* *
* @return {boolean} * @return {Boolean}
*/ */
active(): boolean; active(): boolean;
/** /**
@@ -31,14 +31,14 @@ export default class DiscussionListItem extends Component<import("../../common/C
* should be displayed instead of information about the most recent reply to * should be displayed instead of information about the most recent reply to
* the discussion. * the discussion.
* *
* @return {boolean} * @return {Boolean}
*/ */
showFirstPost(): boolean; showFirstPost(): boolean;
/** /**
* Determine whether or not the number of replies should be shown instead of * Determine whether or not the number of replies should be shown instead of
* the number of unread posts. * the number of unread posts.
* *
* @return {boolean} * @return {Boolean}
*/ */
showRepliesCount(): boolean; showRepliesCount(): boolean;
/** /**
@@ -49,9 +49,9 @@ export default class DiscussionListItem extends Component<import("../../common/C
* Build an item list of info for a discussion listing. By default this is * Build an item list of info for a discussion listing. By default this is
* just the first/last post indicator. * just the first/last post indicator.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
infoItems(): ItemList<import('mithril').Children>; infoItems(): ItemList<any>;
replyCountItem(): JSX.Element; replyCountItem(): JSX.Element;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";

View File

@@ -3,7 +3,6 @@ import Page, { IPageAttrs } from '../../common/components/Page';
import ItemList from '../../common/utils/ItemList'; import ItemList from '../../common/utils/ItemList';
import PostStreamState from '../states/PostStreamState'; import PostStreamState from '../states/PostStreamState';
import Discussion from '../../common/models/Discussion'; import Discussion from '../../common/models/Discussion';
import { ApiResponseSingle } from '../../common/Store';
export interface IDiscussionPageAttrs extends IPageAttrs { export interface IDiscussionPageAttrs extends IPageAttrs {
id: string; id: string;
near?: number; near?: number;
@@ -31,24 +30,34 @@ export default class DiscussionPage<CustomAttrs extends IDiscussionPageAttrs = I
view(): JSX.Element; view(): JSX.Element;
/** /**
* List of components shown while the discussion is loading. * List of components shown while the discussion is loading.
*
* @returns {ItemList}
*/ */
loadingItems(): ItemList<Mithril.Children>; loadingItems(): ItemList<unknown>;
/** /**
* Function that renders the `sidebarItems` ItemList. * Function that renders the `sidebarItems` ItemList.
*
* @returns {import('mithril').Children}
*/ */
sidebar(): Mithril.Children; sidebar(): JSX.Element;
/** /**
* Renders the discussion's hero. * Renders the discussion's hero.
*
* @returns {import('mithril').Children}
*/ */
hero(): Mithril.Children; hero(): JSX.Element;
/** /**
* List of items rendered as the main page content. * List of items rendered as the main page content.
*
* @returns {ItemList}
*/ */
pageContent(): ItemList<Mithril.Children>; pageContent(): ItemList<unknown>;
/** /**
* List of items rendered inside the main page content container. * List of items rendered inside the main page content container.
*
* @returns {ItemList}
*/ */
mainContent(): ItemList<Mithril.Children>; mainContent(): ItemList<unknown>;
/** /**
* Load the discussion from the API or use the preloaded one. * Load the discussion from the API or use the preloaded one.
*/ */
@@ -56,16 +65,23 @@ export default class DiscussionPage<CustomAttrs extends IDiscussionPageAttrs = I
/** /**
* Get the parameters that should be passed in the API request to get the * Get the parameters that should be passed in the API request to get the
* discussion. * discussion.
*
* @return {Object}
*/ */
requestParams(): Record<string, unknown>; requestParams(): {
bySlug: boolean;
page: {
near: number;
};
};
/** /**
* Initialize the component to display the given discussion. * Initialize the component to display the given discussion.
*/ */
show(discussion: ApiResponseSingle<Discussion>): void; show(discussion: Discussion): void;
/** /**
* Build an item list for the contents of the sidebar. * Build an item list for the contents of the sidebar.
*/ */
sidebarItems(): ItemList<Mithril.Children>; sidebarItems(): ItemList<Mithril.Vnode<{}, {}>>;
/** /**
* When the posts that are visible in the post stream change (i.e. the user * When the posts that are visible in the post stream change (i.e. the user
* scrolls up or down), then we update the URL and mark the posts as read. * scrolls up or down), then we update the URL and mark the posts as read.

View File

@@ -17,8 +17,8 @@ export default class EditPostComposer extends ComposerBody {
/** /**
* Get the data to submit to the server when the post is saved. * Get the data to submit to the server when the post is saved.
* *
* @return {Record<string, unknown>} * @return {Object}
*/ */
data(): Record<string, unknown>; data(): Object;
} }
import ComposerBody from "./ComposerBody"; import ComposerBody from "./ComposerBody";

View File

@@ -13,27 +13,27 @@ export default class EventPost extends Post {
/** /**
* Get the name of the event icon. * Get the name of the event icon.
* *
* @return {string} * @return {String}
*/ */
icon(): string; icon(): string;
/** /**
* Get the description text for the event. * Get the description text for the event.
* *
* @param {Record<string, unknown>} data * @param {Object} data
* @return {import('mithril').Children} The description to render in the DOM * @return {String|Object} The description to render in the DOM
*/ */
description(data: Record<string, unknown>): import('mithril').Children; description(data: Object): string | Object;
/** /**
* Get the translation key for the description of the event. * Get the translation key for the description of the event.
* *
* @return {string} * @return {String}
*/ */
descriptionKey(): string; descriptionKey(): string;
/** /**
* Get the translation data for the description of the event. * Get the translation data for the description of the event.
* *
* @return {Record<string, unknown>} * @return {Object}
*/ */
descriptionData(): Record<string, unknown>; descriptionData(): Object;
} }
import Post from "./Post"; import Post from "./Post";

View File

@@ -1,25 +1,25 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" />
import Modal, { IInternalModalAttrs } from '../../common/components/Modal';
import Stream from '../../common/utils/Stream';
import Mithril from 'mithril';
import RequestError from '../../common/utils/RequestError';
export interface IForgotPasswordModalAttrs extends IInternalModalAttrs {
email?: string;
}
/** /**
* The `ForgotPasswordModal` component displays a modal which allows the user to * The `ForgotPasswordModal` component displays a modal which allows the user to
* enter their email address and request a link to reset their password. * enter their email address and request a link to reset their password.
*
* ### Attrs
*
* - `email`
*/ */
export default class ForgotPasswordModal<CustomAttrs extends IForgotPasswordModalAttrs = IForgotPasswordModalAttrs> extends Modal<CustomAttrs> { export default class ForgotPasswordModal extends Modal<import("../../common/components/Modal").IInternalModalAttrs> {
constructor();
/** /**
* The value of the email input. * The value of the email input.
*
* @type {Function}
*/ */
email: Stream<string>; email: Function | undefined;
success: boolean; /**
oninit(vnode: Mithril.Vnode<CustomAttrs, this>): void; * Whether or not the password reset email was sent successfully.
className(): string; *
title(): import("@askvortsov/rich-icu-message-formatter").NestedStringArray; * @type {Boolean}
content(): JSX.Element; */
onsubmit(e: SubmitEvent): void; success: boolean | undefined;
onerror(error: RequestError): void; alert: any;
} }
import Modal from "../../common/components/Modal";

View File

@@ -7,9 +7,9 @@ export default class HeaderPrimary extends Component<import("../../common/Compon
/** /**
* Build an item list for the controls. * Build an item list for the controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -10,47 +10,49 @@ export default class IndexPage extends Page<import("../../common/components/Page
/** /**
* Get the component to display as the hero. * Get the component to display as the hero.
* *
* @return {import('mithril').Children} * @return {MithrilComponent}
*/ */
hero(): import('mithril').Children; hero(): any;
/** /**
* Build an item list for the sidebar of the index page. By default this is a * Build an item list for the sidebar of the index page. By default this is a
* "New Discussion" button, and then a DropdownSelect component containing a * "New Discussion" button, and then a DropdownSelect component containing a
* list of navigation items. * list of navigation items.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
sidebarItems(): ItemList<import('mithril').Children>; sidebarItems(): ItemList<any>;
/** /**
* Build an item list for the navigation in the sidebar of the index page. By * Build an item list for the navigation in the sidebar of the index page. By
* default this is just the 'All Discussions' link. * default this is just the 'All Discussions' link.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
navItems(): ItemList<import('mithril').Children>; navItems(): ItemList<any>;
/** /**
* Build an item list for the part of the toolbar which is concerned with how * Build an item list for the part of the toolbar which is concerned with how
* the results are displayed. By default this is just a select box to change * the results are displayed. By default this is just a select box to change
* the way discussions are sorted. * the way discussions are sorted.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
viewItems(): ItemList<import('mithril').Children>; viewItems(): ItemList<any>;
/** /**
* Build an item list for the part of the toolbar which is about taking action * Build an item list for the part of the toolbar which is about taking action
* on the results. By default this is just a "mark all as read" button. * on the results. By default this is just a "mark all as read" button.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
actionItems(): ItemList<import('mithril').Children>; actionItems(): ItemList<any>;
/** /**
* Open the composer for a new discussion or prompt the user to login. * Open the composer for a new discussion or prompt the user to login.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
newDiscussionAction(): Promise<void>; newDiscussionAction(): Promise<any>;
/** /**
* Mark all discussions as read. * Mark all discussions as read.
*
* @return void
*/ */
markAllAsRead(): void; markAllAsRead(): void;
} }

View File

@@ -6,9 +6,10 @@ export default class LogInButtons extends Component<import("../../common/Compone
/** /**
* Build a list of LogInButton components. * Build a list of LogInButton components.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @public
*/ */
items(): ItemList<import('mithril').Children>; public items(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -1,45 +1,48 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> /**
import Modal, { IInternalModalAttrs } from '../../common/components/Modal'; * The `LogInModal` component displays a modal dialog with a login form.
import ItemList from '../../common/utils/ItemList'; *
import Stream from '../../common/utils/Stream'; * ### Attrs
import type Mithril from 'mithril'; *
import RequestError from '../../common/utils/RequestError'; * - `identification`
export interface ILoginModalAttrs extends IInternalModalAttrs { * - `password`
identification?: string; */
password?: string; export default class LogInModal extends Modal<import("../../common/components/Modal").IInternalModalAttrs> {
remember?: boolean; constructor();
}
export default class LogInModal<CustomAttrs extends ILoginModalAttrs = ILoginModalAttrs> extends Modal<CustomAttrs> {
/** /**
* The value of the identification input. * The value of the identification input.
*
* @type {Function}
*/ */
identification: Stream<string>; identification: Function | undefined;
/** /**
* The value of the password input. * The value of the password input.
*
* @type {Function}
*/ */
password: Stream<string>; password: Function | undefined;
/** /**
* The value of the remember me input. * The value of the remember me input.
*
* @type {Function}
*/ */
remember: Stream<boolean>; remember: Function | undefined;
oninit(vnode: Mithril.Vnode<CustomAttrs, this>): void;
className(): string;
title(): import("@askvortsov/rich-icu-message-formatter").NestedStringArray;
content(): JSX.Element[];
body(): JSX.Element[]; body(): JSX.Element[];
fields(): ItemList<unknown>; fields(): ItemList<any>;
footer(): (string | JSX.Element)[]; footer(): (string | JSX.Element)[];
/** /**
* Open the forgot password modal, prefilling it with an email if the user has * Open the forgot password modal, prefilling it with an email if the user has
* entered one. * entered one.
*
* @public
*/ */
forgotPassword(): void; public forgotPassword(): void;
/** /**
* Open the sign up modal, prefilling it with an email/username/password if * Open the sign up modal, prefilling it with an email/username/password if
* the user has entered one. * the user has entered one.
*
* @public
*/ */
signUp(): void; public signUp(): void;
onready(): void;
onsubmit(e: SubmitEvent): void;
onerror(error: RequestError): void;
} }
import Modal from "../../common/components/Modal";
import ItemList from "../../common/utils/ItemList";

View File

@@ -13,31 +13,31 @@ export default class Notification extends Component<import("../../common/Compone
/** /**
* Get the name of the icon that should be displayed in the notification. * Get the name of the icon that should be displayed in the notification.
* *
* @return {string} * @return {String}
* @abstract * @abstract
*/ */
icon(): string; icon(): string;
/** /**
* Get the URL that the notification should link to. * Get the URL that the notification should link to.
* *
* @return {string} * @return {String}
* @abstract * @abstract
*/ */
href(): string; href(): string;
/** /**
* Get the content of the notification. * Get the content of the notification.
* *
* @return {import('mithril').Children} * @return {VirtualElement}
* @abstract * @abstract
*/ */
content(): import('mithril').Children; content(): any;
/** /**
* Get the excerpt of the notification. * Get the excerpt of the notification.
* *
* @return {import('mithril').Children} * @return {VirtualElement}
* @abstract * @abstract
*/ */
excerpt(): import('mithril').Children; excerpt(): any;
/** /**
* Mark the notification as read. * Mark the notification as read.
*/ */

View File

@@ -11,55 +11,47 @@ export default class NotificationGrid extends Component<import("../../common/Com
/** /**
* Information about the available notification methods. * Information about the available notification methods.
* *
* @type {({ name: string, icon: string, label: import('mithril').Children })[]} * @type {Array}
*/ */
methods: { methods: any[] | undefined;
name: string;
icon: string;
label: import('mithril').Children;
}[] | undefined;
/** /**
* A map of which notification checkboxes are loading. * A map of which notification checkboxes are loading.
* *
* @type {Record<string, boolean>} * @type {Object}
*/ */
loading: Record<string, boolean> | undefined; loading: Object | undefined;
/** /**
* Information about the available notification types. * Information about the available notification types.
* *
* @type {({ name: string, icon: string, label: import('mithril').Children })[]} * @type {Array}
*/ */
types: { types: any[] | undefined;
name: string;
icon: string;
label: import('mithril').Children;
}[] | undefined;
/** /**
* Toggle the state of the given preferences, based on the value of the first * Toggle the state of the given preferences, based on the value of the first
* one. * one.
* *
* @param {string[]} keys * @param {Array} keys
*/ */
toggle(keys: string[]): void; toggle(keys: any[]): void;
/** /**
* Toggle all notification types for the given method. * Toggle all notification types for the given method.
* *
* @param {string} method * @param {String} method
*/ */
toggleMethod(method: string): void; toggleMethod(method: string): void;
/** /**
* Toggle all notification methods for the given type. * Toggle all notification methods for the given type.
* *
* @param {string} type * @param {String} type
*/ */
toggleType(type: string): void; toggleType(type: string): void;
/** /**
* Get the name of the preference key for the given notification type-method * Get the name of the preference key for the given notification type-method
* combination. * combination.
* *
* @param {string} type * @param {String} type
* @param {string} method * @param {String} method
* @return {string} * @return {String}
*/ */
preferenceKey(type: string, method: string): string; preferenceKey(type: string, method: string): string;
/** /**
@@ -71,13 +63,9 @@ export default class NotificationGrid extends Component<import("../../common/Com
* - `icon` The icon to display in the column header. * - `icon` The icon to display in the column header.
* - `label` The label to display in the column header. * - `label` The label to display in the column header.
* *
* @return {ItemList<{ name: string, icon: string, label: import('mithril').Children }>} * @return {ItemList}
*/ */
notificationMethods(): ItemList<{ notificationMethods(): ItemList<any>;
name: string;
icon: string;
label: import('mithril').Children;
}>;
/** /**
* Build an item list for the notification types to display in the grid. * Build an item list for the notification types to display in the grid.
* *
@@ -87,14 +75,9 @@ export default class NotificationGrid extends Component<import("../../common/Com
* - `icon` The icon to display in the notification grid row. * - `icon` The icon to display in the notification grid row.
* - `label` The label to display in the notification grid row. * - `label` The label to display in the notification grid row.
* *
* @return {ItemList<{ name: string, icon: string, label: import('mithril').Children}>} * @return {ItemList}
*/ */
notificationTypes(): ItemList<{ notificationTypes(): ItemList<any>;
name: string;
icon: string;
label: import('mithril').Children;
}>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";
import icon from "../../common/helpers/icon";

View File

@@ -4,7 +4,6 @@
*/ */
export default class NotificationList extends Component<import("../../common/Component").ComponentAttrs, undefined> { export default class NotificationList extends Component<import("../../common/Component").ComponentAttrs, undefined> {
constructor(); constructor();
controlItems(): ItemList<any>;
content(state: any): any; content(state: any): any;
$notifications: JQuery<HTMLElement> | undefined; $notifications: JQuery<HTMLElement> | undefined;
$scrollParent: JQuery<HTMLElement> | JQuery<Window & typeof globalThis> | undefined; $scrollParent: JQuery<HTMLElement> | JQuery<Window & typeof globalThis> | undefined;
@@ -17,4 +16,3 @@ export default class NotificationList extends Component<import("../../common/Com
inPanel(): boolean; inPanel(): boolean;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList";

View File

@@ -1,8 +1,8 @@
export default class NotificationsDropdown extends Dropdown { export default class NotificationsDropdown extends Dropdown {
onclick(): void; onclick(): void;
goToRoute(): void; goToRoute(): void;
getUnreadCount(): number | undefined; getUnreadCount(): any;
getNewCount(): number | undefined; getNewCount(): any;
menuClick(e: any): void; menuClick(e: any): void;
} }
import Dropdown from "../../common/components/Dropdown"; import Dropdown from "../../common/components/Dropdown";

View File

@@ -25,34 +25,34 @@ export default class Post extends Component<import("../../common/Component").Com
/** /**
* Get attributes for the post element. * Get attributes for the post element.
* *
* @return {Record<string, unknown>} * @return {Object}
*/ */
elementAttrs(): Record<string, unknown>; elementAttrs(): Object;
/** /**
* Get the post's content. * Get the post's content.
* *
* @return {import('mithril').Children} * @return {Array}
*/ */
content(): import('mithril').Children; content(): any[];
/** /**
* Get the post's classes. * Get the post's classes.
* *
* @param {string} existing * @param existing string
* @returns {string[]} * @returns {string[]}
*/ */
classes(existing: string): string[]; classes(existing: any): string[];
/** /**
* Build an item list for the post's actions. * Build an item list for the post's actions.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
actionItems(): ItemList<import('mithril').Children>; actionItems(): ItemList<any>;
/** /**
* Build an item list for the post's footer. * Build an item list for the post's footer.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
footerItems(): ItemList<import('mithril').Children>; footerItems(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import SubtreeRetainer from "../../common/utils/SubtreeRetainer"; import SubtreeRetainer from "../../common/utils/SubtreeRetainer";

View File

@@ -12,9 +12,9 @@ export default class PostMeta extends Component<import("../../common/Component")
/** /**
* Get the permalink for the given post. * Get the permalink for the given post.
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @returns {string} * @returns {String}
*/ */
getPermalink(post: import('../../common/models/Post').default): string; getPermalink(post: any): string;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";

View File

@@ -20,17 +20,17 @@ export default class PostStream extends Component<import("../../common/Component
triggerScroll(): void; triggerScroll(): void;
/** /**
* *
* @param {number} top * @param {Integer} top
*/ */
onscroll(top?: number): void; onscroll(top?: any): void;
calculatePositionTimeout: NodeJS.Timeout | undefined; calculatePositionTimeout: NodeJS.Timeout | undefined;
/** /**
* Check if either extreme of the post stream is in the viewport, * Check if either extreme of the post stream is in the viewport,
* and if so, trigger loading the next/previous page. * and if so, trigger loading the next/previous page.
* *
* @param {number} top * @param {Integer} top
*/ */
loadPostsIfNeeded(top?: number): void; loadPostsIfNeeded(top?: any): void;
updateScrubber(top?: number): void; updateScrubber(top?: number): void;
/** /**
* Work out which posts (by number) are currently visible in the viewport, and * Work out which posts (by number) are currently visible in the viewport, and
@@ -41,43 +41,43 @@ export default class PostStream extends Component<import("../../common/Component
* Get the distance from the top of the viewport to the point at which we * Get the distance from the top of the viewport to the point at which we
* would consider a post to be the first one visible. * would consider a post to be the first one visible.
* *
* @return {number} * @return {Integer}
*/ */
getMarginTop(): number; getMarginTop(): any;
/** /**
* Scroll down to a certain post by number and 'flash' it. * Scroll down to a certain post by number and 'flash' it.
* *
* @param {number} number * @param {Integer} number
* @param {boolean} animate * @param {Boolean} animate
* @return {JQueryDeferred} * @return {jQuery.Deferred}
*/ */
scrollToNumber(number: number, animate: boolean): JQueryDeferred<any>; scrollToNumber(number: any, animate: boolean): any;
/** /**
* Scroll down to a certain post by index. * Scroll down to a certain post by index.
* *
* @param {number} index * @param {Integer} index
* @param {boolean} animate * @param {Boolean} animate
* @param {boolean} reply Whether or not to scroll to the reply placeholder. * @param {Boolean} reply Whether or not to scroll to the reply placeholder.
* @return {JQueryDeferred} * @return {jQuery.Deferred}
*/ */
scrollToIndex(index: number, animate: boolean, reply: boolean): JQueryDeferred<any>; scrollToIndex(index: any, animate: boolean, reply: boolean): any;
/** /**
* Scroll down to the given post. * Scroll down to the given post.
* *
* @param {JQuery} $item * @param {jQuery} $item
* @param {boolean} animate * @param {Boolean} animate
* @param {boolean} force Whether or not to force scrolling to the item, even * @param {Boolean} force Whether or not to force scrolling to the item, even
* if it is already in the viewport. * if it is already in the viewport.
* @param {boolean} reply Whether or not to scroll to the reply placeholder. * @param {Boolean} reply Whether or not to scroll to the reply placeholder.
* @return {JQueryDeferred} * @return {jQuery.Deferred}
*/ */
scrollToItem($item: JQuery, animate: boolean, force: boolean, reply: boolean): JQueryDeferred<any>; scrollToItem($item: JQueryStatic, animate: boolean, force: boolean, reply: boolean): any;
/** /**
* 'Flash' the given post, drawing the user's attention to it. * 'Flash' the given post, drawing the user's attention to it.
* *
* @param {JQuery} $item * @param {jQuery} $item
*/ */
flashItem($item: JQuery): void; flashItem($item: JQueryStatic): void;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ScrollListener from "../../common/utils/ScrollListener"; import ScrollListener from "../../common/utils/ScrollListener";

View File

@@ -19,13 +19,9 @@ export default class PostStreamScrubber extends Component<import("../../common/C
* Update the scrollbar's position to reflect the current values of the * Update the scrollbar's position to reflect the current values of the
* index/visible properties. * index/visible properties.
* *
* @param {Partial<{fromScroll: boolean, forceHeightChange: boolean, animate: boolean}>} options * @param {Boolean} animate
*/ */
updateScrubberValues(options?: Partial<{ updateScrubberValues(options?: {}): void;
fromScroll: boolean;
forceHeightChange: boolean;
animate: boolean;
}>): void;
adjustingHeight: boolean | undefined; adjustingHeight: boolean | undefined;
/** /**
* Go to the first post in the discussion. * Go to the first post in the discussion.
@@ -44,16 +40,13 @@ export default class PostStreamScrubber extends Component<import("../../common/C
* Get the percentage of the height of the scrubber that should be allocated * Get the percentage of the height of the scrubber that should be allocated
* to each post. * to each post.
* *
* @return {{ index: number, visible: number }} * @return {Object}
* @property {Number} index The percent per post for posts on either side of * @property {Number} index The percent per post for posts on either side of
* the visible part of the scrubber. * the visible part of the scrubber.
* @property {Number} visible The percent per post for the visible part of the * @property {Number} visible The percent per post for the visible part of the
* scrubber. * scrubber.
*/ */
percentPerPost(): { percentPerPost(): Object;
index: number;
visible: number;
};
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ScrollListener from "../../common/utils/ScrollListener"; import ScrollListener from "../../common/utils/ScrollListener";

View File

@@ -20,35 +20,39 @@ export default class PostsUserPage extends UserPage {
* *
* @type {Post[]} * @type {Post[]}
*/ */
posts: Post[] | undefined; posts: any[] | undefined;
/** /**
* The number of activity items to load per request. * The number of activity items to load per request.
* *
* @type {number} * @type {Integer}
*/ */
loadLimit: number | undefined; loadLimit: any;
/** /**
* Clear and reload the user's activity feed. * Clear and reload the user's activity feed.
*
* @public
*/ */
refresh(): void; public refresh(): void;
/** /**
* Load a new page of the user's activity feed. * Load a new page of the user's activity feed.
* *
* @param {number} [offset] The position to start getting results from. * @param {Integer} [offset] The position to start getting results from.
* @return {Promise<import('../../common/models/Post').default[]>} * @return {Promise}
* @protected * @protected
*/ */
protected loadResults(offset?: number | undefined): Promise<import('../../common/models/Post').default[]>; protected loadResults(offset?: any): Promise<any>;
/** /**
* Load the next page of results. * Load the next page of results.
*
* @public
*/ */
loadMore(): void; public loadMore(): void;
/** /**
* Parse results and append them to the activity feed. * Parse results and append them to the activity feed.
* *
* @param {import('../../common/models/Post').default[]} results * @param {Post[]} results
* @return {import('../../common/models/Post').default[]} * @return {Post[]}
*/ */
parseResults(results: import('../../common/models/Post').default[]): import('../../common/models/Post').default[]; parseResults(results: any[]): any[];
} }
import UserPage from "./UserPage"; import UserPage from "./UserPage";

View File

@@ -16,8 +16,8 @@ export default class ReplyComposer extends ComposerBody {
/** /**
* Get the data to submit to the server when the reply is saved. * Get the data to submit to the server when the reply is saved.
* *
* @return {Record<string, unknown>} * @return {Object}
*/ */
data(): Record<string, unknown>; data(): Object;
} }
import ComposerBody from "./ComposerBody"; import ComposerBody from "./ComposerBody";

View File

@@ -42,22 +42,12 @@ export interface SearchAttrs extends ComponentAttrs {
* *
* - state: SearchState instance. * - state: SearchState instance.
*/ */
export default class Search<T extends SearchAttrs = SearchAttrs> extends Component<T, SearchState> { export default class Search<T extends SearchAttrs = SearchAttrs> extends Component<T> {
/** /**
* The minimum query length before sources are searched. * The minimum query length before sources are searched.
*/ */
protected static MIN_SEARCH_LEN: number; protected static MIN_SEARCH_LEN: number;
/**
* The instance of `SearchState` for this component.
*/
protected searchState: SearchState; protected searchState: SearchState;
/**
* The instance of `SearchState` for this component.
*
* @deprecated Replace with`this.searchState` instead.
*/
protected get state(): SearchState;
protected set state(state: SearchState);
/** /**
* Whether or not the search input has focus. * Whether or not the search input has focus.
*/ */
@@ -65,7 +55,7 @@ export default class Search<T extends SearchAttrs = SearchAttrs> extends Compone
/** /**
* An array of SearchSources. * An array of SearchSources.
*/ */
protected sources?: SearchSource[]; protected sources: SearchSource[];
/** /**
* The number of sources that are still loading results. * The number of sources that are still loading results.
*/ */

View File

@@ -6,9 +6,9 @@ export default class SessionDropdown extends Dropdown {
/** /**
* Build an item list for the contents of the dropdown menu. * Build an item list for the contents of the dropdown menu.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
items(): ItemList<import('mithril').Children>; items(): ItemList<any>;
} }
import Dropdown from "../../common/components/Dropdown"; import Dropdown from "../../common/components/Dropdown";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -6,27 +6,27 @@ export default class SettingsPage extends UserPage {
/** /**
* Build an item list for the user's settings controls. * Build an item list for the user's settings controls.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
settingsItems(): ItemList<import('mithril').Children>; settingsItems(): ItemList<any>;
/** /**
* Build an item list for the user's account settings. * Build an item list for the user's account settings.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
accountItems(): ItemList<import('mithril').Children>; accountItems(): ItemList<any>;
/** /**
* Build an item list for the user's notification settings. * Build an item list for the user's notification settings.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
notificationsItems(): ItemList<import('mithril').Children>; notificationsItems(): ItemList<any>;
/** /**
* Build an item list for the user's privacy settings. * Build an item list for the user's privacy settings.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
privacyItems(): ItemList<import('mithril').Children>; privacyItems(): ItemList<any>;
discloseOnlineLoading: boolean | undefined; discloseOnlineLoading: boolean | undefined;
} }
import UserPage from "./UserPage"; import UserPage from "./UserPage";

View File

@@ -1,53 +1,51 @@
/// <reference path="../../../src/common/translator-icu-rich.d.ts" /> /**
import Modal, { IInternalModalAttrs } from '../../common/components/Modal'; * The `SignUpModal` component displays a modal dialog with a singup form.
import ItemList from '../../common/utils/ItemList'; *
import Stream from '../../common/utils/Stream'; * ### Attrs
import type Mithril from 'mithril'; *
export interface ISignupModalAttrs extends IInternalModalAttrs { * - `username`
username?: string; * - `email`
email?: string; * - `password`
password?: string; * - `token` An email token to sign up with.
token?: string; */
provided?: string[]; export default class SignUpModal extends Modal<import("../../common/components/Modal").IInternalModalAttrs> {
} constructor();
export declare type SignupBody = {
username: string;
email: string;
} & ({
token: string;
} | {
password: string;
});
export default class SignUpModal<CustomAttrs extends ISignupModalAttrs = ISignupModalAttrs> extends Modal<CustomAttrs> {
/** /**
* The value of the username input. * The value of the username input.
*
* @type {Function}
*/ */
username: Stream<string>; username: Function | undefined;
/** /**
* The value of the email input. * The value of the email input.
*
* @type {Function}
*/ */
email: Stream<string>; email: Function | undefined;
/** /**
* The value of the password input. * The value of the password input.
*
* @type {Function}
*/ */
password: Stream<string>; password: Function | undefined;
oninit(vnode: Mithril.Vnode<CustomAttrs, this>): void; isProvided(field: any): any;
className(): string; body(): (string | JSX.Element)[];
title(): import("@askvortsov/rich-icu-message-formatter").NestedStringArray; fields(): ItemList<any>;
content(): JSX.Element[];
isProvided(field: string): boolean;
body(): (false | JSX.Element)[];
fields(): ItemList<unknown>;
footer(): JSX.Element[]; footer(): JSX.Element[];
/** /**
* Open the log in modal, prefilling it with an email/username/password if * Open the log in modal, prefilling it with an email/username/password if
* the user has entered one. * the user has entered one.
*
* @public
*/ */
logIn(): void; public logIn(): void;
onready(): void;
onsubmit(e: SubmitEvent): void;
/** /**
* Get the data that should be submitted in the sign-up request. * Get the data that should be submitted in the sign-up request.
*
* @return {Object}
* @protected
*/ */
submitData(): SignupBody; protected submitData(): Object;
} }
import Modal from "../../common/components/Modal";
import ItemList from "../../common/utils/ItemList";

View File

@@ -15,9 +15,9 @@ export default class UserCard extends Component<import("../../common/Component")
/** /**
* Build an item list of tidbits of info to show on this user's profile. * Build an item list of tidbits of info to show on this user's profile.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
infoItems(): ItemList<import('mithril').Children>; infoItems(): ItemList<any>;
} }
import Component from "../../common/Component"; import Component from "../../common/Component";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -16,36 +16,36 @@ export default class UserPage extends Page<import("../../common/components/Page"
/** /**
* Get the content to display in the user page. * Get the content to display in the user page.
* *
* @return {import('mithril').Children} * @return {VirtualElement}
*/ */
content(): import('mithril').Children; content(): any;
/** /**
* Initialize the component with a user, and trigger the loading of their * Initialize the component with a user, and trigger the loading of their
* activity feed. * activity feed.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @protected * @protected
*/ */
protected show(user: import('../../common/models/User').default): void; protected show(user: any): void;
/** /**
* Given a username, load the user's profile from the store, or make a request * Given a username, load the user's profile from the store, or make a request
* if we don't have it yet. Then initialize the profile page with that user. * if we don't have it yet. Then initialize the profile page with that user.
* *
* @param {string} username * @param {String} username
*/ */
loadUser(username: string): void; loadUser(username: string): void;
/** /**
* Build an item list for the content of the sidebar. * Build an item list for the content of the sidebar.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
sidebarItems(): ItemList<import('mithril').Children>; sidebarItems(): ItemList<any>;
/** /**
* Build an item list for the navigation in the sidebar. * Build an item list for the navigation in the sidebar.
* *
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
*/ */
navItems(): ItemList<import('mithril').Children>; navItems(): ItemList<any>;
} }
import Page from "../../common/components/Page"; import Page from "../../common/components/Page";
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -1,26 +1,13 @@
import Component from '../../common/Component';
import type Mithril from 'mithril';
export interface IWelcomeHeroAttrs {
}
/** /**
* The `WelcomeHero` component displays a hero that welcomes the user to the * The `WelcomeHero` component displays a hero that welcomes the user to the
* forum. * forum.
*/ */
export default class WelcomeHero extends Component<IWelcomeHeroAttrs> { export default class WelcomeHero extends Component<import("../../common/Component").ComponentAttrs, undefined> {
/** constructor();
* @deprecated Extend the `isHidden` method instead. hidden: string | boolean | null | undefined;
*/
hidden: boolean;
oninit(vnode: Mithril.Vnode<IWelcomeHeroAttrs, this>): void;
view(vnode: Mithril.Vnode<IWelcomeHeroAttrs, this>): JSX.Element | null;
/** /**
* Hide the welcome hero. * Hide the welcome hero.
*/ */
hide(): void; hide(): void;
/**
* Determines whether the welcome hero should be hidden.
*
* @returns if the welcome hero is hidden.
*/
isHidden(): boolean;
} }
import Component from "../../common/Component";

View File

@@ -15,9 +15,9 @@ declare class ComposerState {
* The composer's intended height, which can be modified by the user * The composer's intended height, which can be modified by the user
* (by dragging the composer handle). * (by dragging the composer handle).
* *
* @type {number} * @type {Integer}
*/ */
height: number; height: any;
/** /**
* The dynamic component being shown inside the composer. * The dynamic component being shown inside the composer.
* *
@@ -33,15 +33,16 @@ declare class ComposerState {
/** /**
* Load a content component into the composer. * Load a content component into the composer.
* *
* @param {typeof import('../components/ComposerBody').default} componentClass * @param {ComposerBody} componentClass
* @public
*/ */
load(componentClass: typeof import('../components/ComposerBody').default, attrs: any): void; public load(componentClass: any, attrs: any): void;
/** /**
* Clear the composer's content component. * Clear the composer's content component.
*/ */
clear(): void; clear(): void;
onExit: { onExit: {
callback: () => boolean; callback: Function;
message: string; message: string;
} | null | undefined; } | null | undefined;
fields: { fields: {
@@ -49,34 +50,47 @@ declare class ComposerState {
} | undefined; } | undefined;
/** /**
* Show the composer. * Show the composer.
*
* @public
*/ */
show(): void; public show(): void;
/** /**
* Close the composer. * Close the composer.
*
* @public
*/ */
hide(): void; public hide(): void;
/** /**
* Confirm with the user so they don't lose their content, then close the * Confirm with the user so they don't lose their content, then close the
* composer. * composer.
*
* @public
*/ */
close(): void; public close(): void;
/** /**
* Minimize the composer. Has no effect if the composer is hidden. * Minimize the composer. Has no effect if the composer is hidden.
*
* @public
*/ */
minimize(): void; public minimize(): void;
/** /**
* Take the composer into fullscreen mode. Has no effect if the composer is * Take the composer into fullscreen mode. Has no effect if the composer is
* hidden. * hidden.
*
* @public
*/ */
fullScreen(): void; public fullScreen(): void;
/** /**
* Exit fullscreen mode. * Exit fullscreen mode.
*
* @public
*/ */
exitFullScreen(): void; public exitFullScreen(): void;
/** /**
* Determine whether the body matches the given component class and data. * Determine whether the body matches the given component class and data.
* *
* @param {object} type The component class to check against. Subclasses are accepted as well. * @param {object} type The component class to check against. Subclasses are
* accepted as well.
* @param {object} data * @param {object} data
* @return {boolean} * @return {boolean}
*/ */
@@ -96,22 +110,23 @@ declare class ComposerState {
* This will be true if the Composer is in full-screen mode on desktop, * This will be true if the Composer is in full-screen mode on desktop,
* or if we are on a mobile device, where we always consider the composer as full-screen.. * or if we are on a mobile device, where we always consider the composer as full-screen..
* *
* @return {boolean} * @return {Boolean}
* @public
*/ */
isFullScreen(): boolean; public isFullScreen(): boolean;
/** /**
* Check whether or not the user is currently composing a reply to a * Check whether or not the user is currently composing a reply to a
* discussion. * discussion.
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @return {boolean} * @return {Boolean}
*/ */
composingReplyTo(discussion: import('../../common/models/Discussion').default): boolean; composingReplyTo(discussion: any): boolean;
/** /**
* Confirm with the user that they want to close the composer and lose their * Confirm with the user that they want to close the composer and lose their
* content. * content.
* *
* @return {boolean} Whether or not the exit was cancelled. * @return {Boolean} Whether or not the exit was cancelled.
*/ */
preventExit(): boolean; preventExit(): boolean;
/** /**
@@ -121,27 +136,27 @@ declare class ComposerState {
* confirmation is necessary. If the callback returns true at the time of * confirmation is necessary. If the callback returns true at the time of
* closing, the provided text will be shown in a standard confirmation dialog. * closing, the provided text will be shown in a standard confirmation dialog.
* *
* @param {() => boolean} callback * @param {Function} callback
* @param {string} message * @param {String} message
*/ */
preventClosingWhen(callback: () => boolean, message: string): void; preventClosingWhen(callback: Function, message: string): void;
/** /**
* Minimum height of the Composer. * Minimum height of the Composer.
* @returns {number} * @returns {Integer}
*/ */
minimumHeight(): number; minimumHeight(): any;
/** /**
* Maxmimum height of the Composer. * Maxmimum height of the Composer.
* @returns {number} * @returns {Integer}
*/ */
maximumHeight(): number; maximumHeight(): any;
/** /**
* Computed the composer's current height, based on the intended height, and * Computed the composer's current height, based on the intended height, and
* the composer's current state. This will be applied to the composer * the composer's current state. This will be applied to the composer's
* content's DOM element. * content's DOM element.
* @returns {number | string} * @returns {Integer|String}
*/ */
computedHeight(): number | string; computedHeight(): any | string;
} }
declare namespace ComposerState { declare namespace ComposerState {
namespace Position { namespace Position {

View File

@@ -1,6 +1,10 @@
import PaginatedListState, { Page, PaginatedListParams, PaginatedListRequestParams } from '../../common/states/PaginatedListState'; import PaginatedListState, { Page, PaginatedListParams } from '../../common/states/PaginatedListState';
import Discussion from '../../common/models/Discussion'; import Discussion from '../../common/models/Discussion';
import { ApiResponsePlural } from '../../common/Store'; export interface IRequestParams {
include: string[];
filter: Record<string, string>;
sort?: string;
}
export interface DiscussionListParams extends PaginatedListParams { export interface DiscussionListParams extends PaginatedListParams {
sort?: string; sort?: string;
} }
@@ -8,8 +12,8 @@ export default class DiscussionListState<P extends DiscussionListParams = Discus
protected extraDiscussions: Discussion[]; protected extraDiscussions: Discussion[];
constructor(params: P, page?: number); constructor(params: P, page?: number);
get type(): string; get type(): string;
requestParams(): PaginatedListRequestParams; requestParams(): IRequestParams;
protected loadPage(page?: number): Promise<ApiResponsePlural<Discussion>>; protected loadPage(page?: number): Promise<Discussion[]>;
clear(): void; clear(): void;
/** /**
* Get a map of sort keys (which appear in the URL, and are used for * Get a map of sort keys (which appear in the URL, and are used for

View File

@@ -6,7 +6,7 @@ declare class PostStreamState {
* *
* @type {Discussion} * @type {Discussion}
*/ */
discussion: Discussion; discussion: any;
/** /**
* Whether or not the infinite-scrolling auto-load functionality is * Whether or not the infinite-scrolling auto-load functionality is
* disabled. * disabled.
@@ -46,30 +46,33 @@ declare class PostStreamState {
/** /**
* Update the stream so that it loads and includes the latest posts in the * Update the stream so that it loads and includes the latest posts in the
* discussion, if the end is being viewed. * discussion, if the end is being viewed.
*
* @public
*/ */
update(): Promise<void>; public update(): Promise<any>;
visibleEnd: any; visibleEnd: any;
/** /**
* Load and scroll up to the first post in the discussion. * Load and scroll up to the first post in the discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
goToFirst(): Promise<void>; goToFirst(): Promise<any>;
/** /**
* Load and scroll down to the last post in the discussion. * Load and scroll down to the last post in the discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
goToLast(): Promise<void>; goToLast(): Promise<any>;
/** /**
* Load and scroll to a post with a certain number. * Load and scroll to a post with a certain number.
* *
* @param {number | string} number The post number to go to. If 'reply', go to the last post and scroll the reply preview into view. * @param {number|String} number The post number to go to. If 'reply', go to
* @param {boolean} [noAnimation] * the last post and scroll the reply preview into view.
* @return {Promise<void>} * @param {Boolean} noAnimation
* @return {Promise}
*/ */
goToNumber(number: number | string, noAnimation?: boolean | undefined): Promise<void>; goToNumber(number: number | string, noAnimation?: boolean): Promise<any>;
loadPromise: Promise<void> | undefined; loadPromise: Promise<any> | undefined;
needsScroll: boolean | undefined; needsScroll: boolean | undefined;
targetPost: { targetPost: {
number: string | number; number: string | number;
@@ -83,28 +86,28 @@ declare class PostStreamState {
* Load and scroll to a certain index within the discussion. * Load and scroll to a certain index within the discussion.
* *
* @param {number} index * @param {number} index
* @param {boolean} [noAnimation] * @param {Boolean} noAnimation
* @return {Promise<void>} * @return {Promise}
*/ */
goToIndex(index: number, noAnimation?: boolean | undefined): Promise<void>; goToIndex(index: number, noAnimation?: boolean): Promise<any>;
/** /**
* Clear the stream and load posts near a certain number. Returns a promise. * Clear the stream and load posts near a certain number. Returns a promise.
* If the post with the given number is already loaded, the promise will be * If the post with the given number is already loaded, the promise will be
* resolved immediately. * resolved immediately.
* *
* @param {number} number * @param {number} number
* @return {Promise<void>} * @return {Promise}
*/ */
loadNearNumber(number: number): Promise<void>; loadNearNumber(number: number): Promise<any>;
/** /**
* Clear the stream and load posts near a certain index. A page of posts * Clear the stream and load posts near a certain index. A page of posts
* surrounding the given index will be loaded. Returns a promise. If the given * surrounding the given index will be loaded. Returns a promise. If the given
* index is already loaded, the promise will be resolved immediately. * index is already loaded, the promise will be resolved immediately.
* *
* @param {number} index * @param {number} index
* @return {Promise<void>} * @return {Promise}
*/ */
loadNearIndex(index: number): Promise<void>; loadNearIndex(index: number): Promise<any>;
/** /**
* Load the next page of posts. * Load the next page of posts.
*/ */
@@ -119,7 +122,7 @@ declare class PostStreamState {
* *
* @param {number} start * @param {number} start
* @param {number} end * @param {number} end
* @param {boolean} backwards * @param {Boolean} backwards
*/ */
loadPage(start: number, end: number, backwards?: boolean): void; loadPage(start: number, end: number, backwards?: boolean): void;
/** /**
@@ -128,15 +131,15 @@ declare class PostStreamState {
* *
* @param {number} start * @param {number} start
* @param {number} end * @param {number} end
* @return {Promise<void>} * @return {Promise}
*/ */
loadRange(start: number, end: number): Promise<void>; loadRange(start: number, end: number): Promise<any>;
/** /**
* Set up the stream with the given array of posts. * Set up the stream with the given array of posts.
* *
* @param {import('../../common/models/Post').default[]} posts * @param {Post[]} posts
*/ */
show(posts: import('../../common/models/Post').default[]): void; show(posts: any[]): void;
/** /**
* Reset the stream so that a specific range of posts is displayed. If a range * Reset the stream so that a specific range of posts is displayed. If a range
* is not specified, the first page of posts will be displayed. * is not specified, the first page of posts will be displayed.
@@ -150,7 +153,7 @@ declare class PostStreamState {
* *
* @return {Post[]} * @return {Post[]}
*/ */
posts(): Post[]; posts(): any[];
/** /**
* Get the total number of posts in the discussion. * Get the total number of posts in the discussion.
* *
@@ -161,7 +164,7 @@ declare class PostStreamState {
* Check whether or not the scrubber should be disabled, i.e. if all of the * Check whether or not the scrubber should be disabled, i.e. if all of the
* posts are visible in the viewport. * posts are visible in the viewport.
* *
* @return {boolean} * @return {Boolean}
*/ */
disabled(): boolean; disabled(): boolean;
/** /**

View File

@@ -2,151 +2,159 @@ declare namespace _default {
/** /**
* Get a list of controls for a discussion. * Get a list of controls for a discussion.
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @public
*/ */
function controls(discussion: import("../../common/models/Discussion").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(discussion: any, context: any): ItemList<any>;
/** /**
* Get a list of controls for a discussion. * Get a list of controls for a discussion.
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @public
*/ */
function controls(discussion: import("../../common/models/Discussion").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(discussion: any, context: any): ItemList<any>;
/** /**
* Get controls for a discussion pertaining to the current user (e.g. reply, * Get controls for a discussion pertaining to the current user (e.g. reply,
* follow). * follow).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(discussion: import("../../common/models/Discussion").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function userControls(discussion: any, context: any): ItemList<any>;
/** /**
* Get controls for a discussion pertaining to the current user (e.g. reply, * Get controls for a discussion pertaining to the current user (e.g. reply,
* follow). * follow).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(discussion: import("../../common/models/Discussion").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function userControls(discussion: any, context: any): ItemList<any>;
/** /**
* Get controls for a discussion pertaining to moderation (e.g. rename, lock). * Get controls for a discussion pertaining to moderation (e.g. rename, lock).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(discussion: import("../../common/models/Discussion").default): ItemList<import("mithril").Children>; function moderationControls(discussion: any): ItemList<any>;
/** /**
* Get controls for a discussion pertaining to moderation (e.g. rename, lock). * Get controls for a discussion pertaining to moderation (e.g. rename, lock).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(discussion: import("../../common/models/Discussion").default): ItemList<import("mithril").Children>; function moderationControls(discussion: any): ItemList<any>;
/** /**
* Get controls for a discussion which are destructive (e.g. delete). * Get controls for a discussion which are destructive (e.g. delete).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(discussion: import("../../common/models/Discussion").default): ItemList<import("mithril").Children>; function destructiveControls(discussion: any): ItemList<any>;
/** /**
* Get controls for a discussion which are destructive (e.g. delete). * Get controls for a discussion which are destructive (e.g. delete).
* *
* @param {import('../../common/models/Discussion').default} discussion * @param {Discussion} discussion
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(discussion: import("../../common/models/Discussion").default): ItemList<import("mithril").Children>; function destructiveControls(discussion: any): ItemList<any>;
/** /**
* Open the reply composer for the discussion. A promise will be returned, * Open the reply composer for the discussion. A promise will be returned,
* which resolves when the composer opens successfully. If the user is not * which resolves when the composer opens successfully. If the user is not
* logged in, they will be prompted. If they don't have permission to * logged in, they will be prompted. If they don't have permission to
* reply, the promise will be rejected. * reply, the promise will be rejected.
* *
* @param {boolean} goToLast Whether or not to scroll down to the last post if the discussion is being viewed. * @param {Boolean} goToLast Whether or not to scroll down to the last post if
* @param {boolean} forceRefresh Whether or not to force a reload of the composer component, even if it is already open for this discussion. * the discussion is being viewed.
* * @param {Boolean} forceRefresh Whether or not to force a reload of the
* @return {Promise<void>} * composer component, even if it is already open for this discussion.
* @return {Promise}
*/ */
function replyAction(goToLast: boolean, forceRefresh: boolean): Promise<void>; function replyAction(goToLast: boolean, forceRefresh: boolean): Promise<any>;
/** /**
* Open the reply composer for the discussion. A promise will be returned, * Open the reply composer for the discussion. A promise will be returned,
* which resolves when the composer opens successfully. If the user is not * which resolves when the composer opens successfully. If the user is not
* logged in, they will be prompted. If they don't have permission to * logged in, they will be prompted. If they don't have permission to
* reply, the promise will be rejected. * reply, the promise will be rejected.
* *
* @param {boolean} goToLast Whether or not to scroll down to the last post if the discussion is being viewed. * @param {Boolean} goToLast Whether or not to scroll down to the last post if
* @param {boolean} forceRefresh Whether or not to force a reload of the composer component, even if it is already open for this discussion. * the discussion is being viewed.
* * @param {Boolean} forceRefresh Whether or not to force a reload of the
* @return {Promise<void>} * composer component, even if it is already open for this discussion.
* @return {Promise}
*/ */
function replyAction(goToLast: boolean, forceRefresh: boolean): Promise<void>; function replyAction(goToLast: boolean, forceRefresh: boolean): Promise<any>;
/** /**
* Hide a discussion. * Hide a discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function hideAction(): Promise<void>; function hideAction(): Promise<any>;
/** /**
* Hide a discussion. * Hide a discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function hideAction(): Promise<void>; function hideAction(): Promise<any>;
/** /**
* Restore a discussion. * Restore a discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function restoreAction(): Promise<void>; function restoreAction(): Promise<any>;
/** /**
* Restore a discussion. * Restore a discussion.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function restoreAction(): Promise<void>; function restoreAction(): Promise<any>;
/** /**
* Delete the discussion after confirming with the user. * Delete the discussion after confirming with the user.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function deleteAction(): Promise<void>; function deleteAction(): Promise<any>;
/** /**
* Delete the discussion after confirming with the user. * Delete the discussion after confirming with the user.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function deleteAction(): Promise<void>; function deleteAction(): Promise<any>;
/** /**
* Rename the discussion. * Rename the discussion.
*
* @return {Promise}
*/ */
function renameAction(): any; function renameAction(): Promise<any>;
/** /**
* Rename the discussion. * Rename the discussion.
*
* @return {Promise}
*/ */
function renameAction(): any; function renameAction(): Promise<any>;
} }
export default _default; export default _default;
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -44,30 +44,42 @@ export default class Pane {
protected showing: boolean; protected showing: boolean;
/** /**
* Enable the pane. * Enable the pane.
*
* @public
*/ */
enable(): void; public enable(): void;
/** /**
* Disable the pane. * Disable the pane.
*
* @public
*/ */
disable(): void; public disable(): void;
/** /**
* Show the pane. * Show the pane.
*
* @public
*/ */
show(): void; public show(): void;
/** /**
* Hide the pane. * Hide the pane.
*
* @public
*/ */
hide(): void; public hide(): void;
/** /**
* Begin a timeout to hide the pane, which can be cancelled by showing the * Begin a timeout to hide the pane, which can be cancelled by showing the
* pane. * pane.
*
* @public
*/ */
onmouseleave(): void; public onmouseleave(): void;
hideTimeout: NodeJS.Timeout | undefined; hideTimeout: NodeJS.Timeout | undefined;
/** /**
* Toggle whether or not the pane is pinned. * Toggle whether or not the pane is pinned.
*
* @public
*/ */
togglePinned(): void; public togglePinned(): void;
/** /**
* Apply the appropriate CSS classes to the page element. * Apply the appropriate CSS classes to the page element.
* *

View File

@@ -2,129 +2,131 @@ declare namespace _default {
/** /**
* Get a list of controls for a post. * Get a list of controls for a post.
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @public
*/ */
function controls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(post: any, context: any): ItemList<any>;
/** /**
* Get a list of controls for a post. * Get a list of controls for a post.
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @public
*/ */
function controls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post pertaining to the current user (e.g. report). * Get controls for a post pertaining to the current user (e.g. report).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function userControls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post pertaining to the current user (e.g. report). * Get controls for a post pertaining to the current user (e.g. report).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function userControls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post pertaining to moderation (e.g. edit). * Get controls for a post pertaining to moderation (e.g. edit).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function moderationControls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post pertaining to moderation (e.g. edit). * Get controls for a post pertaining to moderation (e.g. edit).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function moderationControls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post that are destructive (e.g. delete). * Get controls for a post that are destructive (e.g. delete).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function destructiveControls(post: any, context: any): ItemList<any>;
/** /**
* Get controls for a post that are destructive (e.g. delete). * Get controls for a post that are destructive (e.g. delete).
* *
* @param {import('../../common/models/Post').default} post * @param {Post} post
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>}')} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(post: import("../../common/models/Post").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function destructiveControls(post: any, context: any): ItemList<any>;
/** /**
* Open the composer to edit a post. * Open the composer to edit a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function editAction(): Promise<void>; function editAction(): Promise<any>;
/** /**
* Open the composer to edit a post. * Open the composer to edit a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function editAction(): Promise<void>; function editAction(): Promise<any>;
/** /**
* Hide a post. * Hide a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function hideAction(): Promise<void>; function hideAction(): Promise<any>;
/** /**
* Hide a post. * Hide a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function hideAction(): Promise<void>; function hideAction(): Promise<any>;
/** /**
* Restore a post. * Restore a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function restoreAction(): Promise<void>; function restoreAction(): Promise<any>;
/** /**
* Restore a post. * Restore a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function restoreAction(): Promise<void>; function restoreAction(): Promise<any>;
/** /**
* Delete a post. * Delete a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function deleteAction(context: any): Promise<void>; function deleteAction(context: any): Promise<any>;
/** /**
* Delete a post. * Delete a post.
* *
* @return {Promise<void>} * @return {Promise}
*/ */
function deleteAction(context: any): Promise<void>; function deleteAction(context: any): Promise<any>;
} }
export default _default; export default _default;
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -2,119 +2,121 @@ declare namespace _default {
/** /**
* Get a list of controls for a user. * Get a list of controls for a user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @public
*/ */
function controls(user: import("../../common/models/User").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(user: any, context: any): ItemList<any>;
/** /**
* Get a list of controls for a user. * Get a list of controls for a user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @public
*/ */
function controls(user: import("../../common/models/User").default, context: import("../../common/Component").default<any, any>): ItemList<import("mithril").Children>; function controls(user: any, context: any): ItemList<any>;
/** /**
* Get controls for a user pertaining to the current user (e.g. poke, follow). * Get controls for a user pertaining to the current user (e.g. poke, follow).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(): ItemList<import("mithril").Children>; function userControls(): ItemList<any>;
/** /**
* Get controls for a user pertaining to the current user (e.g. poke, follow). * Get controls for a user pertaining to the current user (e.g. poke, follow).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function userControls(): ItemList<import("mithril").Children>; function userControls(): ItemList<any>;
/** /**
* Get controls for a user pertaining to moderation (e.g. suspend, edit). * Get controls for a user pertaining to moderation (e.g. suspend, edit).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(user: import("../../common/models/User").default): ItemList<import("mithril").Children>; function moderationControls(user: any): ItemList<any>;
/** /**
* Get controls for a user pertaining to moderation (e.g. suspend, edit). * Get controls for a user pertaining to moderation (e.g. suspend, edit).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function moderationControls(user: import("../../common/models/User").default): ItemList<import("mithril").Children>; function moderationControls(user: any): ItemList<any>;
/** /**
* Get controls for a user which are destructive (e.g. delete). * Get controls for a user which are destructive (e.g. delete).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(user: import("../../common/models/User").default): ItemList<import("mithril").Children>; function destructiveControls(user: any): ItemList<any>;
/** /**
* Get controls for a user which are destructive (e.g. delete). * Get controls for a user which are destructive (e.g. delete).
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {import('../../common/Component').default<any, any>} context The parent component under which the controls menu will be displayed. * @param {*} context The parent component under which the controls menu will
* * be displayed.
* @return {ItemList<import('mithril').Children>} * @return {ItemList}
* @protected * @protected
*/ */
function destructiveControls(user: import("../../common/models/User").default): ItemList<import("mithril").Children>; function destructiveControls(user: any): ItemList<any>;
/** /**
* Delete the user. * Delete the user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
*/ */
function deleteAction(user: import("../../common/models/User").default): void; function deleteAction(user: any): void;
/** /**
* Delete the user. * Delete the user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
*/ */
function deleteAction(user: import("../../common/models/User").default): void; function deleteAction(user: any): void;
/** /**
* Show deletion alert of user. * Show deletion alert of user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {string} type * @param {string} type
*/ */
function showDeletionAlert(user: import("../../common/models/User").default, type: string): void; function showDeletionAlert(user: any, type: string): void;
/** /**
* Show deletion alert of user. * Show deletion alert of user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
* @param {string} type * @param {string} type
*/ */
function showDeletionAlert(user: import("../../common/models/User").default, type: string): void; function showDeletionAlert(user: any, type: string): void;
/** /**
* Edit the user. * Edit the user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
*/ */
function editAction(user: import("../../common/models/User").default): void; function editAction(user: any): void;
/** /**
* Edit the user. * Edit the user.
* *
* @param {import('../../common/models/User').default} user * @param {User} user
*/ */
function editAction(user: import("../../common/models/User").default): void; function editAction(user: any): void;
} }
export default _default; export default _default;
import ItemList from "../../common/utils/ItemList"; import ItemList from "../../common/utils/ItemList";

View File

@@ -1,6 +1,6 @@
/** /**
* Shows an alert if the user has not yet confirmed their email address. * Shows an alert if the user has not yet confirmed their email address.
* *
* @param {import('../ForumApplication').default} app * @param {ForumApplication} app
*/ */
export default function alertEmailConfirmation(app: import('../ForumApplication').default): void; export default function alertEmailConfirmation(app: any): void;

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