<commit_before>// Copyright (c) Jupyter Development Team.
// Distributed under the terms of the Modified BSD License.

import {
  IKernel
} from 'jupyter-js-services';

import {
  DisposableSet
} from 'phosphor/lib/core/disposable';

import {
  IMessageHandler, Message, installMessageHook
} from 'phosphor/lib/core/messaging';

import {
  AttachedProperty
} from 'phosphor/lib/core/properties';

import {
  Widget
} from 'phosphor/lib/ui/widget';

import {
  showDialog
} from '../dialog';

import {
  DocumentRegistry, IDocumentContext, IDocumentModel
} from '../docregistry';

import {
  ContextManager
} from './context';


/**
 * The class name added to document widgets.
 */
const DOCUMENT_CLASS = 'jp-Document';


/**
 * A class that maintains the lifecyle of file-backed widgets.
 */
export
class DocumentWidgetManager {
  /**
   * Construct a new document widget manager.
   */
  constructor(options: DocumentWidgetManager.IOptions) {
    this._contextManager = options.contextManager;
    this._registry = options.registry;
  }

  /**
   * Dispose of the resources used by the widget manager.
   */
  dispose(): void {
    this._registry = null;
    this._contextManager = null;
    for (let id in this._widgets) {
      for (let widget of this._widgets[id]) {
        widget.dispose();
      }
    }
  }

  /**
   * Create a widget for a document and handle its lifecycle.
   */
  createWidget(name: string, id: string, kernel?: IKernel.IModel): Widget {
    let factory = this._registry.getWidgetFactory(name);
    let context = this._contextManager.getContext(id);
    let widget = factory.createNew(context, kernel);
    Private.nameProperty.set(widget, name);

    // Handle widget extensions.
    let disposables = new DisposableSet();
    for (let extender of this._registry.getWidgetExtensions(name)) {
      disposables.add(extender.createNew(widget, context));
    }
    widget.disposed.connect(() => {
      disposables.dispose();
    });
    this.adoptWidget(id, widget);
    return widget;
  }

  /**
   * Install the message hook for the widget and add to list
   * of known widgets.
   */
  adoptWidget(id: string, widget: Widget): void {
    if (!(id in this._widgets)) {
      this._widgets[id] = [];
    }
    this._widgets[id].push(widget);
    installMessageHook(widget, this.filterMessage);
    widget.addClass(DOCUMENT_CLASS);
    widget.title.closable = true;
    widget.disposed.connect(() => {
      // Remove the widget from the widget registry.
      let index = this._widgets[id].indexOf(widget);
      this._widgets[id].splice(index, 1);
      // Dispose of the context if this is the last widget using it.
      if (!this._widgets[id].length) {
        this._contextManager.removeContext(id);
      }
    });
    Private.idProperty.set(widget, id);<commit_msg>Make install message hook has correct context.<commit_after>// Copyright (c) Jupyter Development Team.
// Distributed under the terms of the Modified BSD License.

import {
  IKernel
} from 'jupyter-js-services';

import {
  DisposableSet
} from 'phosphor/lib/core/disposable';

import {
  IMessageHandler, Message, installMessageHook
} from 'phosphor/lib/core/messaging';

import {
  AttachedProperty
} from 'phosphor/lib/core/properties';

import {
  Widget
} from 'phosphor/lib/ui/widget';

import {
  showDialog
} from '../dialog';

import {
  DocumentRegistry, IDocumentContext, IDocumentModel
} from '../docregistry';

import {
  ContextManager
} from './context';


/**
 * The class name added to document widgets.
 */
const DOCUMENT_CLASS = 'jp-Document';


/**
 * A class that maintains the lifecyle of file-backed widgets.
 */
export
class DocumentWidgetManager {
  /**
   * Construct a new document widget manager.
   */
  constructor(options: DocumentWidgetManager.IOptions) {
    this._contextManager = options.contextManager;
    this._registry = options.registry;
  }

  /**
   * Dispose of the resources used by the widget manager.
   */
  dispose(): void {
    this._registry = null;
    this._contextManager = null;
    for (let id in this._widgets) {
      for (let widget of this._widgets[id]) {
        widget.dispose();
      }
    }
  }

  /**
   * Create a widget for a document and handle its lifecycle.
   */
  createWidget(name: string, id: string, kernel?: IKernel.IModel): Widget {
    let factory = this._registry.getWidgetFactory(name);
    let context = this._contextManager.getContext(id);
    let widget = factory.createNew(context, kernel);
    Private.nameProperty.set(widget, name);

    // Handle widget extensions.
    let disposables = new DisposableSet();
    for (let extender of this._registry.getWidgetExtensions(name)) {
      disposables.add(extender.createNew(widget, context));
    }
    widget.disposed.connect(() => {
      disposables.dispose();
    });
    this.adoptWidget(id, widget);
    return widget;
  }

  /**
   * Install the message hook for the widget and add to list
   * of known widgets.
   */
  adoptWidget(id: string, widget: Widget): void {
    if (!(id in this._widgets)) {
      this._widgets[id] = [];
    }
    this._widgets[id].push(widget);
    installMessageHook(widget, (handler: IMessageHandler, msg: Message) => {
      return this.filterMessage(handler, msg);
    });
    widget.addClass(DOCUMENT_CLASS);
    widget.title.closable = true;
    widget.disposed.connect(() => {
      // Remove the widget from the widget registry.
      let index = this._widgets[id].indexOf(widget);
      this._widgets[id].splice(index, 1);
      // Dispose of the context if this is the last widget using it.
      if (!this._widgets[id].length) {
        this._contextManager.removeContext(id);
      }
    });
    Private.idProperty.set(widget, id);
{'fraction_non_alphanumeric': 0.12252756870295817, 'fraction_numerical': 0.00035007876772273763, 'mean_word_length': 3.1616897305171157, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 8, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4250182', 'n_tokens_mistral': 1736, 'n_tokens_neox': 1687, 'n_words': 451}