public setScrollPositionSmooth(update: INewScrollPosition): void {
    if (this._smoothScrollDuration === 0) {
      // Smooth scrolling not supported.
      return this.setScrollPositionNow(update);
    }

    if (this._smoothScrolling) {
      // Combine our pending scrollLeft/scrollTop with incoming scrollLeft/scrollTop
      update = {
        scrollLeft:
          typeof update.scrollLeft === 'undefined'
            ? this._smoothScrolling.to.scrollLeft
            : update.scrollLeft,
        scrollTop:
          typeof update.scrollTop === 'undefined'
            ? this._smoothScrolling.to.scrollTop
            : update.scrollTop,
      };

      // Validate `update`
      const validTarget = this._state.withScrollPosition(update);

      if (
        this._smoothScrolling.to.scrollLeft === validTarget.scrollLeft &&
        this._smoothScrolling.to.scrollTop === validTarget.scrollTop
      ) {
        // No need to interrupt or extend the current animation since we're going to the same place
        return;
      }

      const newSmoothScrolling = this._smoothScrolling.combine(
        this._state,
        validTarget,
        this._smoothScrollDuration,
      );
      this._smoothScrolling.dispose();
      this._smoothScrolling = newSmoothScrolling;
    } else {
      // Validate `update`
      const validTarget = this._state.withScrollPosition(update);

      this._smoothScrolling = SmoothScrollingOperation.start(
        this._state,
        validTarget,
        this._smoothScrollDuration,
      );
    }

    // Begin smooth scrolling animation
    this._smoothScrolling.animationFrameDisposable = this._scheduleAtNextAnimationFrame(() => {
      if (!this._smoothScrolling) {
        return;
      }
      this._smoothScrolling.animationFrameDisposable = null;
      this._performSmoothScrolling();
    });
  }


private _performSmoothScrolling(): void {
    if (!this._smoothScrolling) {
      return;
    }
    const update = this._smoothScrolling.tick();
    const newState = this._state.withScrollPosition(update);

    this._setState(newState);

    if (!this._smoothScrolling) {
      // Looks like someone canceled the smooth scrolling
      // from the scroll event handler
      return;
    }

    if (update.isDone) {
      this._smoothScrolling.dispose();
      this._smoothScrolling = null;
      return;
    }

    // Continue smooth scrolling animation
    this._smoothScrolling.animationFrameDisposable = this._scheduleAtNextAnimationFrame(() => {
      if (!this._smoothScrolling) {
        return;
      }
      this._smoothScrolling.animationFrameDisposable = null;
      this._performSmoothScrolling();
    });
  }


private _setState(newState: ScrollState): void {
    const oldState = this._state;
    if (oldState.equals(newState)) {
      // no change
      return;
    }
    this._state = newState;
    this._onScroll.fire(this._state.createScrollEvent(oldState));
  }


private _initAnimations(): void {
    this.scrollLeft = this._initAnimation(this.from.scrollLeft, this.to.scrollLeft, this.to.width);
    this.scrollTop = this._initAnimation(this.from.scrollTop, this.to.scrollTop, this.to.height);
  }


private _initAnimation(from: number, to: number, viewportSize: number): IAnimation {
    const delta = Math.abs(from - to);
    if (delta > 2.5 * viewportSize) {
      let stop1: number;
      let stop2: number;
      if (from < to) {
        // scroll to 75% of the viewportSize
        stop1 = from + 0.75 * viewportSize;
        stop2 = to - 0.75 * viewportSize;
      } else {
        stop1 = from - 0.75 * viewportSize;
        stop2 = to + 0.75 * viewportSize;
      }
      return createComposed(createEaseOutCubic(from, stop1), createEaseOutCubic(stop2, to), 0.33);
    }
    return createEaseOutCubic(from, to);
  }


public dispose(): void {
    if (this.animationFrameDisposable !== null) {
      this.animationFrameDisposable.dispose();
      this.animationFrameDisposable = null;
    }
  }


public acceptScrollDimensions(state: ScrollState): void {
    this.to = state.withScrollPosition(this.to);
    this._initAnimations();
  }


public tick(): SmoothScrollingUpdate {
    return this._tick(Date.now());
  }


protected _tick(now: number): SmoothScrollingUpdate {
    const completion = (now - this._startTime) / this.duration;

    if (completion < 1) {
      const newScrollLeft = this.scrollLeft(completion);
      const newScrollTop = this.scrollTop(completion);
      return new SmoothScrollingUpdate(newScrollLeft, newScrollTop, false);
    }

    return new SmoothScrollingUpdate(this.to.scrollLeft, this.to.scrollTop, true);
  }


public combine(
    from: ISmoothScrollPosition,
    to: ISmoothScrollPosition,
    duration: number,
  ): SmoothScrollingOperation {
    return SmoothScrollingOperation.start(from, to, duration);
  }


public static start(
    from: ISmoothScrollPosition,
    to: ISmoothScrollPosition,
    duration: number,
  ): SmoothScrollingOperation {
    // +10 / -10 : pretend the animation already started for a quicker response to a scroll request
    duration += 10;
    const startTime = Date.now() - 10;

    return new SmoothScrollingOperation(from, to, startTime, duration);
  }


() => {
  beforeEach(() => {

    TestBed.configureTestingModule({
      imports: [HttpClientTestingModule],
      providers: [AdministrationService]
    })
  })

  it('should be created', inject([AdministrationService], (service: AdministrationService) => {
    expect(service).toBeTruthy()
  }))

  it('should get application version directly from the rest api', inject([AdministrationService, HttpTestingController],
    fakeAsync((service: AdministrationService, httpMock: HttpTestingController) => {
      let res
      service.getApplicationVersion().subscribe((data) => res = data)
      const req = httpMock.expectOne('http://localhost:3000/rest/admin/application-version')
      req.flush({ version: 'apiResponse' })
      tick()

      expect(req.request.method).toBe('GET')
      expect(res).toBe('apiResponse')
      httpMock.verify()
    })
  ))
}


() => {

    TestBed.configureTestingModule({
      imports: [HttpClientTestingModule],
      providers: [AdministrationService]
    })
  }


(service: AdministrationService) => {
    expect(service).toBeTruthy()
  }


(service: AdministrationService, httpMock: HttpTestingController) => {
      let res
      service.getApplicationVersion().subscribe((data) => res = data)
      const req = httpMock.expectOne('http://localhost:3000/rest/admin/application-version')
      req.flush({ version: 'apiResponse' })
      tick()

      expect(req.request.method).toBe('GET')
      expect(res).toBe('apiResponse')
      httpMock.verify()
    }


(data) => res = data


data => console.log(data)


async (req: NextApiRequest, res: NextApiResponse, ctx: IRequestContext) => {
  const { param: dateOrMagic, format } = extractFormat(req, 'date', extractDateOrMagic);
  const date = dateOrMagic instanceof Date ? dateOrMagic : await resolveMetaDate(dateOrMagic, ctx);
  const region = extractRegion(req);
  const data = () => fetchRegion(ctx, region, date);
  return sendFormat(req, res, ctx, format, data, {
    title: `${region.name}-${formatAPIDate(date)}`,
    cache: estimateCacheDuration(date),
    constantFields: {
      date,
      region: region.id,
    },
  });
}


() => fetchRegion(ctx, region, date)


(_) => Formula


(_) => SPEC


(p) => p.startsWith(`icon_chara_all_${this.DF.toString().padStart(4, '0')}`)


(p) => `img/icon_chara/Texture2D/${p}`


(df) => Object.values(dataManager.files.img.icon_chara.Texture2D)
      .filter((p) => p.startsWith(`icon_chara_all_${df.toString().padStart(4, '0')}`))
      .map((p) => `img/icon_chara/Texture2D/${p}`)
      .filter((p) => !images.includes(p))


(p) => p.startsWith(`icon_chara_all_${df.toString().padStart(4, '0')}`)


(p) => !images.includes(p)


(p) => [p, dataManager.questById[p.QUEST_DF]]


([, quest]) => quest


(p) => p.LV


(p) => p.key()


(p) => ({
        level: p.key(),
        skills: p.select((i) => dataManager.skillById[i.DF])
          .where((p) => !!p)
          .toArray(),
      })


(i) => dataManager.skillById[i.DF]


(p) => !!p


(p) => p.LV <= level


(p) => dataManager.skillById[p.DF]


(p) => p


(skill) => skill.withComboSkills


(p) => p.id


(p) => p.NO >= startLevel && p.NO <= endLevel


(p) => p.FD


(p) => p.DF


(p) => ({
        item: dataManager.itemById[p.key()],
        qualities: p.groupBy((o) => o.QTY).select((o) => ({
          quality: o.key(),
          count: o.count(),
        })).orderBy((o) => o.quality).toArray(),
      })


(o) => o.QTY


(o) => ({
          quality: o.key(),
          count: o.count(),
        })


(o) => o.quality


(p) => !!p.item


(p) => p.item.DF


(p) => dataManager.lookup.elementMapSkillEffectTarget[element].includes(p.effectTarget) && p.effect === EBattleEffectKind.eSTATUS_FIX


(sum, p) => sum + p.effectValue


(element) => this.getElement(element, level)


(p) => p.effectTarget === dataManager.lookup.stateMapSkillEffectTarget[state]


(p) => p.effectTarget === dataManager.lookup.stateMapSkillEffectTarget[state] && p.effect === EBattleEffectKind.eSTATUS_FIX


(state) => this.getState(state, level, foodLevel)


(_) => MVList


export class SPEC {
  @Type((_) => Formula)
  HP: Formula;
  @Type((_) => Formula)
  SATK: Formula;
  @Type((_) => Formula)
  SDEF: Formula;
  @Type((_) => Formula)
  MATK: Formula;
  @Type((_) => Formula)
  MDEF: Formula;
  @Type((_) => Formula)
  SPD: Formula;
  @Type((_) => Formula)
  SDA: Formula;
  @Type((_) => Formula)
  LDA: Formula;
  @Type((_) => Formula)
  QTH: Formula;
  @Type((_) => Formula)
  DDG: Formula;
  @Type((_) => Formula)
  SADD: Formula;
}


export class Chara {
  m_GameObject: MGameObject;
  m_Enabled: number;
  m_Script: MScript;
  m_Name: string;

  @Type((_) => MVList)
  m_vList: MVList[];
}


// custom types
export interface IElementResult {
  element: string;
  label: string;
  skills: SkillList[],
  value: number;
  total: number;
}


export interface IStateResult {
  state: string;
  label: string;
  skills: SkillList[],
  value: number;
  foodValue: number;
  skillValue: number;
  total: number;
}


// generated types
export interface MGameObject {
  m_FileID: number;
  m_PathID: number;
}


export interface MScript {
  m_FileID: number;
  m_PathID: number;
}


export interface SKILL {
  DF: number;
  LV: number;
}


export interface FD {
  DF: number;
  QTY: number;
}


export interface FDM {
  NO: number;
  GRD: number;
  FD: FD[];
  HP: number;
  SATK: number;
  SDEF: number;
  MATK: number;
  MDEF: number;
  SPD: number;
  SDA: number;
  LDA: number;
  QTH: number;
  DDG: number;
  SADD: number;
}


export interface QST {
  NO: number;
  QUEST_DF: number;
  FLAG_DF: number;
  LV: number;
}


export interface WEAPON {
  GEN: number;
}


export interface GROW {
  STAR: number;
  STONE: number;
}


export interface AvHelmOffset {
  id: number;
  offsetY: number;
}


export interface MDL {
  fScale: number;
  eAnimKind: number;
  avHelmOffset: AvHelmOffset[];
  bMacho: number;
  hairId: number;
  eyeId: number;
  headId: number;
  voice: number;
  weaponId: number;
  bodyId: number;
  shieldId: number;
  helmId: number;
  accId1: number;
  accId2: number;
  accId3: number;
}


export interface BA {
  LV: number;
  DF: number;
}


// skills
public getRawSkills(level = MVList.maxLevel) {
    return this.SKILL
      .filter((p) => p.LV <= level)
      .map((p) => dataManager.skillById[p.DF])
      .filter((p) => p);
  }


public getSkills(level = MVList.maxLevel) {
    const key = JSON.stringify({ level });
    if (!this.#skillCache.has(key)) {
      this.#skillCache.set(key, SkillList.removeOverrideSkills(this.getRawSkills(level)));
    }
    return this.#skillCache.get(key);
  }


public getSkillWithComboSkills(level = MVList.maxLevel) {
    const key = JSON.stringify({ level });
    if (!this.#skillWithComboSkillCache.has(key)) {
      const skills = SkillList.removeOverrideSkills(this.getRawSkills(level))
        .map((skill) => skill.withComboSkills)
        .flat();
      this.#skillWithComboSkillCache.set(key, Enumerable.from(skills).distinct((p) => p.id).toArray());
    }
    return this.#skillWithComboSkillCache.get(key);
  }


public getBlazeArt(level = MVList.maxLevel, blazeArtLevel = 5) {
    const blazeArts = this.BA.filter((p) => p.LV <= level);
    if (!blazeArts.length) {
      return null;
    }
    const blazeArtLv = dataManager.blazeArtById[blazeArts[0].DF].LV;
    const blazeArt = blazeArtLv[blazeArtLevel - 1];
    return dataManager.skillById[blazeArt?.SKILL_DF];
  }


public totalFoods(startLevel = 1, endLevel = MVList.maxLevel) {
    return Enumerable.from(this.FDM)
      .where((p) => p.NO >= startLevel && p.NO <= endLevel)
      .selectMany((p) => p.FD)
      .groupBy((p) => p.DF)
      .select((p) => ({
        item: dataManager.itemById[p.key()],
        qualities: p.groupBy((o) => o.QTY).select((o) => ({
          quality: o.key(),
          count: o.count(),
        })).orderBy((o) => o.quality).toArray(),
      }))
      .where((p) => !!p.item)
      .orderBy((p) => p.item.DF)
      .toArray();
  }


//
public getElement(element: string, level = MVList.maxLevel) {
    const key = JSON.stringify({ element, level });
    if (!this.#elementCache.has(key)) {
      const skills = this.getSkillWithComboSkills(level)
        .filter((p) => dataManager.lookup.elementMapSkillEffectTarget[element].includes(p.effectTarget) && p.effect === EBattleEffectKind.eSTATUS_FIX);
      const result = {
        element,
        label: dataManager.lookup.element[element],
        value: skills.reduce((sum, p) => sum + p.effectValue, 0),
        skills,
        total: 0,
      };
      result.total = result.value;
      this.#elementCache.set(key, result);
    }
    return this.#elementCache.get(key);
  }


public getElements(level = MVList.maxLevel) {
    return Object.keys(dataManager.lookup.element).map((element) => this.getElement(element, level));
  }


//
public getFoodSpec(level = MVList.maxLevel) {
    return this.FDM[level - 1];
  }


public getFoodState(state: string, foodLevel = MVList.maxLevel) {
    return this.getFoodSpec(foodLevel)?.[state] ?? 0;
  }


public getBaseState(state: string, level = MVList.maxLevel) {
    return this.SPEC[state].getValue(level);
  }


public getState(state: string, level = MVList.maxLevel, foodLevel = MVList.maxLevel) {
    const key = JSON.stringify({ state, level, foodLevel });
    if (!this.#stateCache.has(key)) {
      const baseSkills = this.getSkillWithComboSkills(level);
      const skills = ['QTH', 'DDG'].includes(state)
        ? baseSkills.filter((p) => p.effectTarget === dataManager.lookup.stateMapSkillEffectTarget[state])
        : baseSkills.filter((p) => p.effectTarget === dataManager.lookup.stateMapSkillEffectTarget[state] && p.effect === EBattleEffectKind.eSTATUS_FIX);
      const result = {
        state,
        label: dataManager.lookup.state[state],
        value: this.getBaseState(state, level),
        foodValue: this.getFoodState(state, foodLevel),
        skillValue: skills.reduce((sum, p) => sum + p.effectValue, 0),
        total: 0,
        skills,
      };
      result.total = result.value + result.foodValue + result.skillValue;
      this.#stateCache.set(key, result);
    }
    return this.#stateCache.get(key);
  }


public getStates(level = MVList.maxLevel, foodLevel = MVList.maxLevel) {
    return Object.keys(this.SPEC).map((state) => this.getState(state, level, foodLevel));
  }


export class GroupDTO {
    @IsString()
    @IsNotEmpty()
    readonly name: string;

    @IsString()
    readonly description: string;

    @IsArray()
    readonly permissions: Array<Permission>
}


function Modal({
  imgURL,
  isModalVisible,
  setIsModalVisible,
  roomId,
  questionId,
  type,
}: IModalProps) {
  const history = useHistory();

  async function handleDeleteQuestion() {
    await database.ref(`rooms/${roomId}/questions/${questionId}`).remove().then(() => {
      ShowToast({ type: 'success', message: 'Question deleted' });
    });

    setIsModalVisible(false);
  }

  async function handleEndRoom() {
    await database.ref(`rooms/${roomId}`).update({
      endedAt: new Date(),
    }).then(() => {
      ShowToast({ type: 'success', message: 'Room deleted' });
    });

    history.push('/');
  }

  return (

{(type === 'delete') ? 'Remover pergunta' : 'Encerrar Sala'}


async function handleDeleteQuestion() {
    await database.ref(`rooms/${roomId}/questions/${questionId}`).remove().then(() => {
      ShowToast({ type: 'success', message: 'Question deleted' });
    });

    setIsModalVisible(false);
  }


async function handleEndRoom() {
    await database.ref(`rooms/${roomId}`).update({
      endedAt: new Date(),
    }).then(() => {
      ShowToast({ type: 'success', message: 'Room deleted' });
    });

    history.push('/');
  }


() => {
      ShowToast({ type: 'success', message: 'Question deleted' });
    }


() => {
      ShowToast({ type: 'success', message: 'Room deleted' });
    }


() => setIsModalVisible(false)


type IModalProps = {
  imgURL: string;
  isModalVisible: boolean;
  setIsModalVisible: (isModalVisible: boolean) => void;
  roomId: string | undefined;
  questionId: string | undefined;
  type: string;
}


export default function JSDebuggerStatement(): Token {
	return concat(["debugger", ";"]);
}


export default class VisitorContext {
    output = {
        types: {},
        interfaces: {}
    };
    sg: sg.SchemaGenerator;
    typeChecker: ts.TypeChecker;

    constructor(private program: ts.Program,
                public name: string,
                public nssPrefix: string,
                public vendor: string,
                public version: string,
                private schemaGeneratorConfig: sg.Config = {}) {
        this.typeChecker = program.getTypeChecker();
    }

    getSchemaGenerator() {
        if (!this.sg) {
            const config: sg.Config = {
                topRef: true,
                expose: 'export',
                jsDoc: 'extended',
                extraTags: [],
                ...this.schemaGeneratorConfig
            };
            log('Creating schema generator with config', config);
            const parser = sg.createParser(this.program, config);
            this.sg = new sg.SchemaGenerator(this.program, parser, sg.createFormatter(config));
        }
        return this.sg;
    }
}


getSchemaGenerator() {
        if (!this.sg) {
            const config: sg.Config = {
                topRef: true,
                expose: 'export',
                jsDoc: 'extended',
                extraTags: [],
                ...this.schemaGeneratorConfig
            };
            log('Creating schema generator with config', config);
            const parser = sg.createParser(this.program, config);
            this.sg = new sg.SchemaGenerator(this.program, parser, sg.createFormatter(config));
        }
        return this.sg;
    }


export function inc(params: Array<number> /*, hash*/) {
    return params[0] + 1;
}


(draft: Draft<XkcdState>, action: XkcdActionsUnion): void => {
  switch (action.type) {
    case XkcdActionType.SET_ERROR:
      draft.error = action.payload
      break

    case XkcdActionType.SET_INFO:
      draft.info = action.payload
      break

    case XkcdActionType.SET_LOADING_STATE:
      draft.loadingState = action.payload
      break
  }
}


props => (
    <div className="web-content">
        <PageTitle title


export interface BatchChangesSiteConfigSettingsAreaProps extends Pick<RouteComponentProps, 'history' | 'location'> {
    queryGlobalBatchChangesCodeHosts?: typeof queryGlobalBatchChangesCodeHosts
}


() => {
  let component: JobboardsComponent;
  let fixture: ComponentFixture<JobboardsComponent>;

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      declarations: [ JobboardsComponent ]
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(JobboardsComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

  it('should create', () => {
    expect(component).toBeTruthy();
  });
}


() => {
    TestBed.configureTestingModule({
      declarations: [ JobboardsComponent ]
    })
    .compileComponents();
  }


() => {
    fixture = TestBed.createComponent(JobboardsComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  }


function splitBoxes(pq: PQueue<VBox>, target: number): void {
  let lastSize = pq.size;

  while (pq.size < target) {
    const vbox = pq.pop();

    if (!vbox || vbox.count < 1) {
      break;
    }

    const [vbox1, vbox2] = vbox.split();

    pq.push(vbox1);
    if (vbox2 && vbox2.count > 0) pq.push(vbox2);

    // No more new boxes, converged
    if (pq.size === lastSize) {
      break;
    } else {
      lastSize = pq.size;
    }
  }
}


function generateSwatches(pq: PQueue<VBox>) {
  const swatches: Swatch[] = [];

  while (pq.size) {
    const v = pq.pop();
    const color = v.avg;
    swatches.push(new Swatch(color, v.count));
  }

  return swatches;
}


(pixels: Pixels, opts: ComputedOptions): Array<Swatch> => {
  if (pixels.length === 0 || opts.colorCount < 2 || opts.colorCount > 256) {
    throw new Error('Wrong MMCQ parameters');
  }

  const vbox = VBox.build(pixels);
  const pq = new PQueue<VBox>((a, b) => a.count - b.count);

  pq.push(vbox);

  // first set of colors, sorted by population
  splitBoxes(pq, fractByPopulations * opts.colorCount);

  // Re-order
  const pq2 = new PQueue<VBox>((a, b) => a.count * a.volume - b.count * b.volume);
  pq2.contents = pq.contents;

  // next set - generate the median cuts using the (npix * vol) sorting.
  splitBoxes(pq2, opts.colorCount - pq2.size);

  // calculate the actual colors
  return generateSwatches(pq2);
}


(a, b) => a.count - b.count


(a, b) => a.count * a.volume - b.count * b.volume


(name?: string): CharacterSkill => ({
  name: name || '',
  info: '',
  rotations: '',
  tips: '',
})


(): PositionalInfo => ({
  position: '',
  builds: '',
  rotations: '',
  tips: '',
})


(endpoint: string): string => {
  return urlJoin(API_ROOT, endpoint);
}


beforeEach() {
		emitter = new Evented();
		source = new EventedStreamSource(emitter, 'testEvent');
		stream = new ReadableStream<Event>(source);
		reader = stream.getReader();

		return stream.started;
	}


start() {
			emitter.emit(testEvent);

			return reader.read().then(function (result: ReadResult<Event>) {
				assert.strictEqual(result.value, testEvent as any,
					'Event read from stream should be the same as the event emitted by emitter');
			});
		}


'event array'() {
			let appleEvent = {
				type: 'apple',
				test: 'value'
			};
			let orangeEvent = {
				type: 'orange',
				test: 'value'
			};

			source = new EventedStreamSource(emitter, [ 'apple', 'orange' ]);
			stream = new ReadableStream<Event>(source);
			reader = stream.getReader();

			emitter.emit(appleEvent);
			emitter.emit(orangeEvent);

			return reader.read().then(function (result: ReadResult<Event>) {
				assert.strictEqual(result.value, appleEvent as any);

				return reader.read().then(function (result: ReadResult<Event>) {
					assert.strictEqual(result.value, orangeEvent as any);
				});
			});
		}


cancel() {
			let enqueueCallCount = 0;

			stream.controller.enqueue = function (chunk: Event) {
				enqueueCallCount += 1;
			};

			source.cancel();
			emitter.emit(testEvent);
			assert.strictEqual(enqueueCallCount, 0, 'Canceled source should not call controller.enqueue');
		}


(props: Props) => {
  const {
    section,
    search,
    count,
    onlyOnSale,
    isMap,
    wearableRarities,
    wearableGenders,
    contracts,
    onBrowse
  } = props

  const [showFiltersMenu, setShowFiltersMenu] = useState(false)
  const [showFiltersModal, setShowFiltersModal] = useState(false)

  const category = section ? getSearchCategory(section) : undefined
  const dropdownOptions = [
    { value: SortBy.NEWEST, text: t('filters.newest') },
    { value: SortBy.NAME, text: t('filters.name') }
  ]

  if (onlyOnSale) {
    dropdownOptions.unshift({
      value: SortBy.RECENTLY_LISTED,
      text: t('filters.recently_listed')
    })
    dropdownOptions.unshift({
      value: SortBy.CHEAPEST,
      text: t('filters.cheapest')
    })
  }

  const sortBy = dropdownOptions.find(option => option.value === props.sortBy)
    ? props.sortBy
    : dropdownOptions[0].value

  const appliedFilters = []
  if (wearableRarities.length > 0) {
    appliedFilters.push(t('nft_filters.rarity'))
  }
  // if (wearableGenders.length > 0) {
  //   appliedFilters.push(t('nft_filters.gender'))
  // }
  // if (contracts.length > 0) {
  //   appliedFilters.push(t('nft_filters.collection'))
  // }

  const handleOnlyOnSaleChange = useCallback(
    (_, props: CheckboxProps) => {
      onBrowse({ sortBy: SortBy.NEWEST, onlyOnSale: !!props.checked })
    },
    [onBrowse]
  )

  const handleIsMapChange = useCallback(
    (isMap: boolean) => {
      onBrowse({ isMap, isFullscreen: false, search: '' })
    },
    [onBrowse]
  )

  const handleDropdownChange = useCallback(
    (_, props: DropdownProps) => {
      onBrowse({ sortBy: props.value as SortBy })
    },
    [onBrowse]
  )

  const handleRaritiesChange = useCallback(
    (options: string[]) => {
      const newOptions = options.map((option) => t(`wearable.rarity.${option}`).toLowerCase())
      onBrowse({ wearableRarities: newOptions as WearableRarity[] })
    },
    [onBrowse]
  )

  const handleGendersChange = useCallback(
    (options: string[]) => {
      onBrowse({ wearableGenders: options as WearableGender[] })
    },
    [onBrowse]
  )

  const handleCollectionsChange = useCallback(
    (contract: string) => {
      onBrowse({ contracts: [contract as ContractName] })
    },
    [onBrowse]
  )

  const handleSearch = useCallback(
    (newSearch: string) => {
      if (search !== newSearch) {
        onBrowse({ search: newSearch, isMap: false, isFullscreen: false })
      }
    },
    [search, onBrowse]
  )

  // const handleToggleFilterMenu = useCallback(
  //   () => setShowFiltersMenu(!showFiltersMenu),
  //   [showFiltersMenu, setShowFiltersMenu]
  // )

  useEffect(() => setShowFiltersMenu(false), [category, setShowFiltersMenu])

  const searchPlaceholder = isMap
    ? t('nft_filters.search_land')
    : count === undefined
      ? t('global.loading') + '...'
      : t('nft_filters.search', {
        suffix:
          count < MAX_QUERY_SIZE
            ? t('nft_filters.results', {
              count: count.toLocaleString()
            })
            : t('nft_filters.more_than_results', {
              count: count.toLocaleString()
            })
      })

  return (

        {isMap ? (
          <>
            <TextFilter
              value={search}
              placeholder={searchPlaceholder}
              onChange={handleSearch}
            />
            <Responsive
              minWidth={Responsive.onlyTablet.minWidth}
              className="topbar-filter"
            >
              <Radio
                toggle
                checked={onlyOnSale}
                onChange={handleOnlyOnSaleChange}
                label={t('nft_filters.on_sale')}
              />
            </Responsive>
          </>


option => option.value === props.sortBy


(_, props: CheckboxProps) => {
      onBrowse({ sortBy: SortBy.NEWEST, onlyOnSale: !!props.checked })
    }


(isMap: boolean) => {
      onBrowse({ isMap, isFullscreen: false, search: '' })
    }


(_, props: DropdownProps) => {
      onBrowse({ sortBy: props.value as SortBy })
    }


(options: string[]) => {
      const newOptions = options.map((option) => t(`wearable.rarity.${option}`).toLowerCase())
      onBrowse({ wearableRarities: newOptions as WearableRarity[] })
    }


(option) => t(`wearable.rarity.${option}`).toLowerCase()


(options: string[]) => {
      onBrowse({ wearableGenders: options as WearableGender[] })
    }


(contract: string) => {
      onBrowse({ contracts: [contract as ContractName] })
    }


(newSearch: string) => {
      if (search !== newSearch) {
        onBrowse({ search: newSearch, isMap: false, isFullscreen: false })
      }
    }


() => setShowFiltersMenu(false)


isMap ? (
          <


t('global.apply')


export class MasterPlanOnly {
    requestName: string;
	sponsor: string;
	coSponsor: string;
	requestedStartyear: number;
	goal: string;
    constructor() {
        this.requestName = "";
        this.sponsor = "";
        this.coSponsor = "";
        this.requestedStartyear = 0;
        this.goal = "";
    }
}


export type Appointment = {
    id: string,
    psychologistId: string,
    appointmentDate: string,
    patientId: string,
    deleted: boolean
}


() => {
        // make sure the target is the active editor so we do not
        // commit prematurely
        if (activeNode && activeNode.contains(target) && this.grid.getEditorLock().isActive()) {
          this.grid.getEditorLock().commitCurrentEdit();
        }
      }


(processResult: GraphqlResult) => {
          const datasetName = (backendApi && backendApi.service && typeof backendApi.service.getDatasetName === 'function') ? backendApi.service.getDatasetName() : '';
          if (processResult && processResult.data && processResult.data[datasetName]) {
            this._dataset = processResult.data[datasetName].nodes;
            if (processResult.data[datasetName].listSeparator) {
              // if the "listSeparator" is available in the GraphQL result, we'll override the ExportOptions Delimiter with this new info
              if (!this.gridOptions.exportOptions) {
                this.gridOptions.exportOptions = {};
              }
              this.gridOptions.exportOptions.delimiterOverride = processResult.data[datasetName].listSeparator.toString();
            }
            this.refreshGridData(this._dataset, processResult.data[datasetName].totalCount);
          } else {
            this._dataset = [];
          }
        }


(event) => {
          if (gridOptions.enableTranslate) {
            this.extensionService.translateColumnHeaders();
            this.extensionService.translateColumnPicker();
            this.extensionService.translateGridMenu();
            this.extensionService.translateHeaderMenu();
          }
        }


(e: any, args: any) => {
          return this.dispatchCustomEvent(`${slickgridEventPrefix}${titleCase(prop)}`, { eventData: e, args });
        }


(gridStateChange: GridStateChange) => {
        this.onGridStateChanged.emit(gridStateChange);
      }


(e: any, args: any) => {
        grid.invalidate();
      }


(e: any, args: any) => {
          if (args && args.rows && Array.isArray(args.rows)) {
            args.rows.forEach((row) => grid.updateRow(row));
            grid.render();
          }
        }


(row) => grid.updateRow(row)


(rowNumber: number) => {
        const item = this.dataView.getItem(rowNumber);
        return gridOptions.colspanCallback(item);
      }


() => {
        // keep start time & end timestamps & return it after process execution
        const startTime = new Date();

        // run any pre-process, if defined, for example a spinner
        if (backendApi.preProcess) {
          backendApi.preProcess();
        }

        try {
          // the processes can be Observables (like HttpClient) or Promises
          if (process instanceof Promise && process.then) {
            process.then((processResult: GraphqlResult | any) => executeBackendProcessesCallback(startTime, processResult, backendApi, this.gridOptions.pagination.totalItems));
          } else if (isObservable(process)) {
            process.subscribe(
              (processResult: GraphqlResult | any) => executeBackendProcessesCallback(startTime, processResult, backendApi, this.gridOptions.pagination.totalItems),
              (error: any) => onBackendError(error, backendApi)
            );
          }
        } catch (error) {
          onBackendError(error, backendApi);
        }
      }


(processResult: GraphqlResult | any) => executeBackendProcessesCallback(startTime, processResult, backendApi, this.gridOptions.pagination.totalItems)


(error: any) => onBackendError(error, backendApi)


(resolvedCollection) => this.updateEditorCollection(column, resolvedCollection)


(column: Column | any) => {
      // on every Editor that have a "collectionAsync", resolve the data and assign it to the "collection" property
      if (column.editor && column.editor.collectionAsync) {
        this.loadEditorCollectionAsync(column);
      }
      return { ...column, editor: column.editor && column.editor.model, internalColumnEditor: { ...column.editor } };
    }


(col: Column) => col.id === column.id


ngOnInit(): void {
    this.onBeforeGridCreate.emit(true);

    if (this.gridOptions && !this.gridOptions.enableAutoResize && (this._fixedHeight || this._fixedWidth)) {
      this.gridHeightString = `${this._fixedHeight}px`;
      this.gridWidthString = `${this._fixedWidth}px`;
    }
  }


ngOnDestroy(): void {
    this.onBeforeGridDestroy.emit(this.grid);
    this.destroy();
    this.onAfterGridDestroyed.emit(true);
  }


destroy(emptyDomElementContainer = false) {
    const gridContainerId = this.gridOptions && this.gridOptions.gridContainerId;
    this.dataView = undefined;
    this.gridOptions = {};
    this.extensionService.dispose();
    this.filterService.dispose();
    this.gridEventService.dispose();
    this.gridStateService.dispose();
    this.groupingAndColspanService.dispose();
    this.paginationService.dispose();
    this.resizer.dispose();
    this.sortService.dispose();
    if (this._eventHandler && this._eventHandler.unsubscribeAll) {
      this._eventHandler.unsubscribeAll();
    }
    if (this.grid && this.grid.destroy) {
      this.grid.destroy();
    }

    if (emptyDomElementContainer) {
      $(gridContainerId).empty();
    }

    // also unsubscribe all RxJS subscriptions
    this.subscriptions = unsubscribeAllObservables(this.subscriptions);
  }


ngAfterViewInit() {
    this.initialization();
    this.isGridInitialized = true;

    // user must provide a "gridHeight" or use "autoResize: true" in the grid options
    if (!this._fixedHeight && !this.gridOptions.enableAutoResize) {
      throw new Error(
        `[Angular-Slickgrid] requires a "grid-height" or the "enableAutoResize" grid option to be enabled.
        Without that the grid will seem empty while in fact it just does not have any height define.`
      );
    }
  }


initialization() {
    // make sure the dataset is initialized (if not it will throw an error that it cannot getLength of null)
    this._dataset = this._dataset || [];
    this.gridOptions = this.mergeGridOptions(this.gridOptions);
    this.paginationOptions = this.gridOptions.pagination;
    this.locales = this.gridOptions && this.gridOptions.locales || Constants.locales;
    this.backendServiceApi = this.gridOptions && this.gridOptions.backendServiceApi;
    this.createBackendApiInternalPostProcessCallback(this.gridOptions);

    if (!this.customDataView) {
      if (this.gridOptions.draggableGrouping || this.gridOptions.enableGrouping) {
        this.extensionUtility.loadExtensionDynamically(ExtensionName.groupItemMetaProvider);
        this.groupItemMetadataProvider = new Slick.Data.GroupItemMetadataProvider();
        this.sharedService.groupItemMetadataProvider = this.groupItemMetadataProvider;
        this.dataView = new Slick.Data.DataView({ groupItemMetadataProvider: this.groupItemMetadataProvider });
      } else {
        this.dataView = new Slick.Data.DataView();
      }
    }

    // for convenience to the user, we provide the property "editor" as an Angular-Slickgrid editor complex object
    // however "editor" is used internally by SlickGrid for it's own Editor Factory
    // so in our lib we will swap "editor" and copy it into a new property called "internalColumnEditor"
    // then take back "editor.model" and make it the new "editor" so that SlickGrid Editor Factory still works
    this._columnDefinitions = this.swapInternalEditorToSlickGridFactoryEditor(this._columnDefinitions);

    // save reference for all columns before they optionally become hidden/visible
    this.sharedService.allColumns = this._columnDefinitions;
    this.sharedService.visibleColumns = this._columnDefinitions;
    this.extensionService.createExtensionsBeforeGridCreation(this._columnDefinitions, this.gridOptions);

    // build SlickGrid Grid, also user might optionally pass a custom dataview (e.g. remote model)
    this.grid = new Slick.Grid(`#${this.gridId}`, this.customDataView || this.dataView, this._columnDefinitions, this.gridOptions);

    this.sharedService.dataView = this.dataView;
    this.sharedService.grid = this.grid;

    this.extensionService.bindDifferentExtensions();
    this.bindDifferentHooks(this.grid, this.gridOptions, this.dataView);

    // emit the Grid & DataView object to make them available in parent component
    this.onGridCreated.emit(this.grid);

    // initialize the SlickGrid grid
    this.grid.init();

    if (!this.customDataView && (this.dataView && this.dataView.beginUpdate && this.dataView.setItems && this.dataView.endUpdate)) {
      this.onDataviewCreated.emit(this.dataView);
      this.dataView.beginUpdate();
      this.dataView.setItems(this._dataset, this.gridOptions.datasetIdPropertyName);
      this.dataView.endUpdate();

      // if you don't want the items that are not visible (due to being filtered out or being on a different page)
      // to stay selected, pass 'false' to the second arg
      if (this.gridOptions && this.gridOptions.dataView && this.gridOptions.dataView.hasOwnProperty('syncGridSelection')) {
        const syncGridSelection = this.gridOptions.dataView.syncGridSelection;
        if (typeof syncGridSelection === 'boolean') {
          this.dataView.syncGridSelection(this.grid, this.gridOptions.dataView.syncGridSelection);
        } else {
          this.dataView.syncGridSelection(this.grid, syncGridSelection.preserveHidden, syncGridSelection.preserveHiddenOnSelectionChange);
        }
      }
    }

    // user might want to hide the header row on page load but still have `enableFiltering: true`
    // if that is the case, we need to hide the headerRow ONLY AFTER all filters got created & dataView exist
    if (this._hideHeaderRowAfterPageLoad) {
      this.showHeaderRow(false);
    }

    // after the DataView is created & updated execute some processes
    this.executeAfterDataviewCreated(this.grid, this.gridOptions, this.dataView);

    // bind resize ONLY after the dataView is ready
    this.bindResizeHook(this.grid, this.gridOptions);

    // bind & initialize grouping and header grouping colspan service
    if (this.gridOptions.createPreHeaderPanel && !this.gridOptions.enableDraggableGrouping) {
      this.groupingAndColspanService.init(this.grid, this.dataView);
    }

    // bind & initialize the grid service
    this.gridService.init(this.grid, this.dataView);

    // when user enables translation, we need to translate Headers on first pass & subsequently in the bindDifferentHooks
    if (this.gridOptions.enableTranslate) {
      this.extensionService.translateColumnHeaders();
    }

    // if Export is enabled, initialize the service with the necessary grid and other objects
    if (this.gridOptions.enableExport) {
      this.exportService.init(this.grid, this.dataView);
    }

    // if Excel Export is enabled, initialize the service with the necessary grid and other objects
    if (this.gridOptions.enableExcelExport && this.sharedService) {
      // create an instance of the ExcelExportService only when required (opt-in)
      this.excelExportService = new ExcelExportService(this.translate);
      this.onGridBeforeExportToExcel = this.excelExportService.onGridBeforeExportToExcel;
      this.onGridAfterExportToExcel = this.excelExportService.onGridAfterExportToExcel;
      this.excelExportService.init(this.grid, this.dataView);
    }

    // once all hooks are in placed and the grid is initialized, we can emit an event
    this.onGridInitialized.emit(this.grid);

    // bind the Backend Service API callback functions only after the grid is initialized
    // because the preProcess() and onInit() might get triggered
    if (this.gridOptions && this.gridOptions.backendServiceApi) {
      this.bindBackendCallbackFunctions(this.gridOptions);
    }

    this.gridStateService.init(this.grid);

    this.onAngularGridCreated.emit({
      // Slick Grid & DataView objects
      dataView: this.dataView,
      slickGrid: this.grid,

      // public methods
      destroy: this.destroy.bind(this),

      // return all available Services (non-singleton)
      backendService: this.gridOptions && this.gridOptions.backendServiceApi && this.gridOptions.backendServiceApi.service,
      excelExportService: this.excelExportService,
      exportService: this.exportService,
      extensionService: this.extensionService,
      filterService: this.filterService,
      gridEventService: this.gridEventService,
      gridStateService: this.gridStateService,
      gridService: this.gridService,
      groupingService: this.groupingAndColspanService,
      paginationService: this.paginationService,
      resizerService: this.resizer,
      sortService: this.sortService,

      /** @deprecated please use "extensionService" instead */
      pluginService: this.extensionService,
    });
  }


/**
   * Commits the current edit to the grid
   */
commitEdit(target: Element) {
    if (this.grid.getOptions().autoCommitEdit) {
      const activeNode = this.grid.getActiveCellNode();

      // a timeout must be set or this could come into conflict when slickgrid
      // tries to commit the edit when going from one editor to another on the grid
      // through the click event. If the timeout was not here it would
      // try to commit/destroy the editor twice, which would throw a jquery
      // error about the element not being in the DOM
      setTimeout(() => {
        // make sure the target is the active editor so we do not
        // commit prematurely
        if (activeNode && activeNode.contains(target) && this.grid.getEditorLock().isActive()) {
          this.grid.getEditorLock().commitCurrentEdit();
        }
      });
    }
  }


/**
   * Define our internal Post Process callback, it will execute internally after we get back result from the Process backend call
   * For now, this is GraphQL Service ONLY feature and it will basically refresh the Dataset & Pagination without having the user to create his own PostProcess every time
   */
createBackendApiInternalPostProcessCallback(gridOptions: GridOption) {
    const backendApi = gridOptions && gridOptions.backendServiceApi;
    if (backendApi) {
      // internalPostProcess only works (for now) with a GraphQL Service, so make sure it is that type
      if (backendApi && backendApi.service instanceof GraphqlService) {
        backendApi.internalPostProcess = (processResult: GraphqlResult) => {
          const datasetName = (backendApi && backendApi.service && typeof backendApi.service.getDatasetName === 'function') ? backendApi.service.getDatasetName() : '';
          if (processResult && processResult.data && processResult.data[datasetName]) {
            this._dataset = processResult.data[datasetName].nodes;
            if (processResult.data[datasetName].listSeparator) {
              // if the "listSeparator" is available in the GraphQL result, we'll override the ExportOptions Delimiter with this new info
              if (!this.gridOptions.exportOptions) {
                this.gridOptions.exportOptions = {};
              }
              this.gridOptions.exportOptions.delimiterOverride = processResult.data[datasetName].listSeparator.toString();
            }
            this.refreshGridData(this._dataset, processResult.data[datasetName].totalCount);
          } else {
            this._dataset = [];
          }
        };
      }
    }
  }


bindDifferentHooks(grid: any, gridOptions: GridOption, dataView: any) {
    // on locale change, we have to manually translate the Headers, GridMenu
    if (this.translate && this.translate.onLangChange) {
      this.subscriptions.push(
        this.translate.onLangChange.subscribe((event) => {
          if (gridOptions.enableTranslate) {
            this.extensionService.translateColumnHeaders();
            this.extensionService.translateColumnPicker();
            this.extensionService.translateGridMenu();
            this.extensionService.translateHeaderMenu();
          }
        })
      );
    }

    // if user entered some Columns "presets", we need to reflect them all in the grid
    if (gridOptions.presets && Array.isArray(gridOptions.presets.columns) && gridOptions.presets.columns.length > 0) {
      const gridColumns: Column[] = this.gridStateService.getAssociatedGridColumns(grid, gridOptions.presets.columns);
      if (gridColumns && Array.isArray(gridColumns) && gridColumns.length > 0) {
        // make sure that the checkbox selector is also visible if it is enabled
        if (gridOptions.enableCheckboxSelector) {
          const checkboxColumn = (Array.isArray(this._columnDefinitions) && this._columnDefinitions.length > 0) ? this._columnDefinitions[0] : null;
          if (checkboxColumn && checkboxColumn.id === '_checkbox_selector' && gridColumns[0].id !== '_checkbox_selector') {
            gridColumns.unshift(checkboxColumn);
          }
        }

        // finally set the new presets columns (including checkbox selector if need be)
        grid.setColumns(gridColumns);
      }
    }

    // bind external sorting (backend) when available or default onSort (dataView)
    if (gridOptions.enableSorting && !this.customDataView) {
      gridOptions.backendServiceApi ? this.sortService.bindBackendOnSort(grid, dataView) : this.sortService.bindLocalOnSort(grid, dataView);
    }

    // bind external filter (backend) when available or default onFilter (dataView)
    if (gridOptions.enableFiltering && !this.customDataView) {
      this.filterService.init(grid);

      // if user entered some Filter "presets", we need to reflect them all in the DOM
      if (gridOptions.presets && Array.isArray(gridOptions.presets.filters) && gridOptions.presets.filters.length > 0) {
        this.filterService.populateColumnFilterSearchTermPresets(gridOptions.presets.filters);
      }
      gridOptions.backendServiceApi ? this.filterService.bindBackendOnFilter(grid, this.dataView) : this.filterService.bindLocalOnFilter(grid, this.dataView);
    }

    // if user set an onInit Backend, we'll run it right away (and if so, we also need to run preProcess, internalPostProcess & postProcess)
    if (gridOptions.backendServiceApi) {
      const backendApi = gridOptions.backendServiceApi;

      if (backendApi && backendApi.service && backendApi.service.init) {
        backendApi.service.init(backendApi.options, gridOptions.pagination, this.grid);
      }
    }

    // expose all Slick Grid Events through dispatch
    for (const prop in grid) {
      if (grid.hasOwnProperty(prop) && prop.startsWith('on')) {
        this._eventHandler.subscribe(grid[prop], (e: any, args: any) => {
          return this.dispatchCustomEvent(`${slickgridEventPrefix}${titleCase(prop)}`, { eventData: e, args });
        });
      }
    }

    // expose all Slick DataView Events through dispatch
    for (const prop in dataView) {
      if (dataView.hasOwnProperty(prop) && prop.startsWith('on')) {
        this._eventHandler.subscribe(dataView[prop], (e: any, args: any) => {
          return this.dispatchCustomEvent(`${slickgridEventPrefix}${titleCase(prop)}`, { eventData: e, args });
        });
      }
    }

    // expose GridState Service changes event through dispatch
    this.subscriptions.push(
      this.gridStateService.onGridStateChanged.subscribe((gridStateChange: GridStateChange) => {
        this.onGridStateChanged.emit(gridStateChange);
      })
    );

    // on cell click, mainly used with the columnDef.action callback
    this.gridEventService.bindOnCellChange(grid, dataView);
    this.gridEventService.bindOnClick(grid, dataView);

    if (dataView && grid) {
      this._eventHandler.subscribe(dataView.onRowCountChanged, (e: any, args: any) => {
        grid.invalidate();
      });

      // without this, filtering data with local dataset will not always show correctly
      // also don't use "invalidateRows" since it destroys the entire row and as bad user experience when updating a row
      // see commit: https://github.com/ghiscoding/Angular-Slickgrid/commit/bb62c0aa2314a5d61188ff005ccb564577f08805
      if (gridOptions && gridOptions.enableFiltering && !gridOptions.enableRowDetailView) {
        this._eventHandler.subscribe(dataView.onRowsChanged, (e: any, args: any) => {
          if (args && args.rows && Array.isArray(args.rows)) {
            args.rows.forEach((row) => grid.updateRow(row));
            grid.render();
          }
        });
      }
    }

    // does the user have a colspan callback?
    if (gridOptions.colspanCallback) {
      this.dataView.getItemMetadata = (rowNumber: number) => {
        const item = this.dataView.getItem(rowNumber);
        return gridOptions.colspanCallback(item);
      };
    }
  }


bindBackendCallbackFunctions(gridOptions: GridOption) {
    const backendApi = gridOptions.backendServiceApi;
    const serviceOptions: BackendServiceOption = (backendApi && backendApi.service && backendApi.service.options) ? backendApi.service.options : {};
    const isExecuteCommandOnInit = (!serviceOptions) ? false : ((serviceOptions && serviceOptions.hasOwnProperty('executeProcessCommandOnInit')) ? serviceOptions['executeProcessCommandOnInit'] : true);

    // update backend filters (if need be) before the query runs
    if (backendApi) {
      const backendService = backendApi.service;

      // if user entered some any "presets", we need to reflect them all in the grid
      if (gridOptions && gridOptions.presets) {
        // Filters "presets"
        if (backendService && backendService.updateFilters && Array.isArray(gridOptions.presets.filters) && gridOptions.presets.filters.length > 0) {
          backendService.updateFilters(gridOptions.presets.filters, true);
        }
        // Sorters "presets"
        if (backendService && backendService.updateSorters && Array.isArray(gridOptions.presets.sorters) && gridOptions.presets.sorters.length > 0) {
          backendService.updateSorters(undefined, gridOptions.presets.sorters);
        }
        // Pagination "presets"
        if (backendService && backendService.updatePagination && gridOptions.presets.pagination) {
          backendService.updatePagination(gridOptions.presets.pagination.pageNumber, gridOptions.presets.pagination.pageSize);
        }
      } else {
        const columnFilters = this.filterService.getColumnFilters();
        if (columnFilters && backendService && backendService.updateFilters) {
          backendService.updateFilters(columnFilters, false);
        }
      }
    }

    if (backendApi && backendApi.service && (backendApi.onInit || isExecuteCommandOnInit)) {
      const query = (typeof backendApi.service.buildQuery === 'function') ? backendApi.service.buildQuery() : '';
      const process = (isExecuteCommandOnInit) ? backendApi.process(query) : backendApi.onInit(query);

      // wrap this inside a setTimeout to avoid timing issue since the gridOptions needs to be ready before running this onInit
      setTimeout(() => {
        // keep start time & end timestamps & return it after process execution
        const startTime = new Date();

        // run any pre-process, if defined, for example a spinner
        if (backendApi.preProcess) {
          backendApi.preProcess();
        }

        try {
          // the processes can be Observables (like HttpClient) or Promises
          if (process instanceof Promise && process.then) {
            process.then((processResult: GraphqlResult | any) => executeBackendProcessesCallback(startTime, processResult, backendApi, this.gridOptions.pagination.totalItems));
          } else if (isObservable(process)) {
            process.subscribe(
              (processResult: GraphqlResult | any) => executeBackendProcessesCallback(startTime, processResult, backendApi, this.gridOptions.pagination.totalItems),
              (error: any) => onBackendError(error, backendApi)
            );
          }
        } catch (error) {
          onBackendError(error, backendApi);
        }
      });
    }
  }


bindResizeHook(grid: any, options: GridOption) {
    // expand/autofit columns on first page load
    if (grid && options.autoFitColumnsOnFirstLoad && options.enableAutoSizeColumns) {
      grid.autosizeColumns();

      // compensate anytime SlickGrid measureScrollbar is incorrect (only seems to happen in Chrome 1/5 computers)
      this.resizer.compensateHorizontalScroll(this.grid, this.gridOptions);
    }

    // auto-resize grid on browser resize
    if (this._fixedHeight || this._fixedWidth) {
      this.resizer.init(grid, { height: this._fixedHeight, width: this._fixedWidth });
    } else {
      this.resizer.init(grid);
    }
    if (options.enableAutoResize) {
      this.resizer.bindAutoResizeDataGrid();
      if (grid && options.autoFitColumnsOnFirstLoad && options.enableAutoSizeColumns) {
        grid.autosizeColumns();
      }
    }
  }


executeAfterDataviewCreated(grid: any, gridOptions: GridOption, dataView: any) {
    // if user entered some Sort "presets", we need to reflect them all in the DOM
    if (gridOptions.enableSorting) {
      if (gridOptions.presets && Array.isArray(gridOptions.presets.sorters) && gridOptions.presets.sorters.length > 0) {
        this.sortService.loadLocalGridPresets(grid, dataView);
      }
    }
  }


mergeGridOptions(gridOptions): GridOption {
    gridOptions.gridId = this.gridId;
    gridOptions.gridContainerId = `slickGridContainer-${this.gridId}`;

    // use jquery extend to deep merge & copy to avoid immutable properties being changed in GlobalGridOptions after a route change
    const options = $.extend(true, {}, GlobalGridOptions, this.forRootConfig, gridOptions);

    // using jQuery extend to do a deep clone has an unwanted side on objects and pageSizes but ES6 spread has other worst side effects
    // so we will just overwrite the pageSizes when needed, this is the only one causing issues so far.
    // jQuery wrote this on their docs:: On a deep extend, Object and Array are extended, but object wrappers on primitive types such as String, Boolean, and Number are not.
    if (gridOptions && gridOptions.backendServiceApi) {
      if (gridOptions.pagination && Array.isArray(gridOptions.pagination.pageSizes) && gridOptions.pagination.pageSizes.length > 0) {
        options.pagination.pageSizes = gridOptions.pagination.pageSizes;
      }
    }

    // also make sure to show the header row if user have enabled filtering
    this._hideHeaderRowAfterPageLoad = (options.showHeaderRow === false);
    if (options.enableFiltering && !options.showHeaderRow) {
      options.showHeaderRow = options.enableFiltering;
    }
    return options;
  }


/**
   * On a Pagination changed, we will trigger a Grid State changed with the new pagination info
   * Also if we use Row Selection or the Checkbox Selector, we need to reset any selection
   */
paginationChanged(pagination: Pagination) {
    if (this.gridOptions.enableRowSelection || this.gridOptions.enableCheckboxSelector) {
      this.gridService.setSelectedRows([]);
    }

    this.gridStateService.onGridStateChanged.next({
      change: { newValues: pagination, type: GridStateType.pagination },
      gridState: this.gridStateService.getCurrentGridState()
    });
  }


/**
   * When dataset changes, we need to refresh the entire grid UI & possibly resize it as well
   * @param dataset
   */
refreshGridData(dataset: any[], totalCount?: number) {
    if (Array.isArray(dataset) && this.grid && this.dataView && typeof this.dataView.setItems === 'function') {
      this.dataView.setItems(dataset, this.gridOptions.datasetIdPropertyName);
      if (!this.gridOptions.backendServiceApi) {
        this.dataView.reSort();
      }

      if (dataset) {
        this.grid.invalidate();
        this.grid.render();
      }

      if (this.gridOptions && this.gridOptions.backendServiceApi && this.gridOptions.pagination) {
        // do we want to show pagination?
        // if we have a backendServiceApi and the enablePagination is undefined, we'll assume that we do want to see it, else get that defined value
        this.showPagination = ((this.gridOptions.backendServiceApi && this.gridOptions.enablePagination === undefined) ? true : this.gridOptions.enablePagination) || false;

        if (this.gridOptions.presets && this.gridOptions.presets.pagination && this.gridOptions.pagination) {
          this.paginationOptions.pageSize = this.gridOptions.presets.pagination.pageSize;
          this.paginationOptions.pageNumber = this.gridOptions.presets.pagination.pageNumber;
        }

        // when we have a totalCount use it, else we'll take it from the pagination object
        // only update the total items if it's different to avoid refreshing the UI
        const totalRecords = totalCount !== undefined ? totalCount : this.gridOptions.pagination.totalItems;
        if (totalRecords !== this.totalItems) {
          this.totalItems = totalRecords;
        }
      } else {
        // without backend service, we'll assume the total of items is the dataset size
        this.totalItems = dataset.length;
      }

      // resize the grid inside a slight timeout, in case other DOM element changed prior to the resize (like a filter/pagination changed)
      if (this.grid && this.gridOptions.enableAutoResize) {
        const delay = this.gridOptions.autoResize && this.gridOptions.autoResize.delay;
        this.resizer.resizeGrid(delay || 10);
      }
    }
  }


/**
   * Dynamically change or update the column definitions list.
   * We will re-render the grid so that the new header and data shows up correctly.
   * If using i18n, we also need to trigger a re-translate of the column headers
   */
updateColumnDefinitionsList(newColumnDefinitions) {
    // map/swap the internal library Editor to the SlickGrid Editor factory
    newColumnDefinitions = this.swapInternalEditorToSlickGridFactoryEditor(newColumnDefinitions);

    if (this.gridOptions.enableTranslate) {
      this.extensionService.translateColumnHeaders(false, newColumnDefinitions);
    } else {
      this.extensionService.renderColumnHeaders(newColumnDefinitions);
    }

    if (this.gridOptions && this.gridOptions.enableAutoSizeColumns) {
      this.grid.autosizeColumns();
    }
  }


/** Toggle the filter row displayed on first row
   * @param isShowing
   */
showHeaderRow(isShowing: boolean) {
    this.grid.setHeaderRowVisibility(isShowing);
    return isShowing;
  }


/** Toggle the filter row displayed on first row */
toggleHeaderRow() {
    const isShowing = !this.grid.getOptions().showHeaderRow;
    this.grid.setHeaderRowVisibility(isShowing);
    return isShowing;
  }


//
// private functions
// ------------------
/** Dispatch of Custom Event, which by default will bubble & is cancelable */
private dispatchCustomEvent(eventName: string, data?: any, isBubbling: boolean = true, isCancelable: boolean = true) {
    const eventInit: CustomEventInit = { bubbles: isBubbling, cancelable: isCancelable };
    if (data) {
      eventInit.detail = data;
    }
    return this.elm.nativeElement.dispatchEvent(new CustomEvent(eventName, eventInit));
  }


/** Load the Editor Collection asynchronously and replace the "collection" property when Observable resolves */
private loadEditorCollectionAsync(column: Column) {
    const collectionAsync = column && column.editor && column.editor.collectionAsync;
    if (collectionAsync instanceof Observable) {
      this.subscriptions.push(
        collectionAsync.subscribe((resolvedCollection) => this.updateEditorCollection(column, resolvedCollection))
      );
    }
  }


/**
   * For convenience to the user, we provide the property "editor" as an Angular-Slickgrid editor complex object
   * however "editor" is used internally by SlickGrid for it's own Editor Factory
   * so in our lib we will swap "editor" and copy it into a new property called "internalColumnEditor"
   * then take back "editor.model" and make it the new "editor" so that SlickGrid Editor Factory still works
   */
private swapInternalEditorToSlickGridFactoryEditor(columnDefinitions: Column[]) {
    return columnDefinitions.map((column: Column | any) => {
      // on every Editor that have a "collectionAsync", resolve the data and assign it to the "collection" property
      if (column.editor && column.editor.collectionAsync) {
        this.loadEditorCollectionAsync(column);
      }
      return { ...column, editor: column.editor && column.editor.model, internalColumnEditor: { ...column.editor } };
    });
  }


/**
   * Update the Editor "collection" property from an async call resolved
   * Since this is called after the async call resolves, the pointer will not be the same as the "column" argument passed.
   * Once we found the new pointer, we will reassign the "editor" and "collection" to the "internalColumnEditor" so it has newest collection
   */
private updateEditorCollection(column: Column, newCollection: any[]) {
    column.editor.collection = newCollection;

    // find the new column reference pointer
    const columns = this.grid.getColumns();
    if (Array.isArray(columns)) {
      const columnRef: Column = columns.find((col: Column) => col.id === column.id);
      columnRef.internalColumnEditor = column.editor;
    }
  }


(props: ISvgIconProps) => (
        <svg
            width={props.size}


export interface FlagMap {
	readonly [key: string]: {
		readonly char?: AlphabetLowercase;
		readonly description: string;
	};
}


export type AlphabetLowercase =
	| 'a'
	| 'b'
	| 'c'
	| 'd'
	| 'e'
	| 'f'
	| 'g'
	| 'h'
	| 'i'
	| 'j'
	| 'k'
	| 'l'
	| 'm'
	| 'n'
	| 'o'
	| 'p'
	| 'q'
	| 'r'
	| 's'
	| 't'
	| 'u'
	| 'v'
	| 'w'
	| 'x'
	| 'y'
	| 'z';


@Component({
    selector: 'list-item',
    templateUrl: './list.item.component.html',
    styleUrls: ['./list.item.component.css']
})

export class ListItemComponent implements OnInit {
    @Input('title') title: String;
    @Input('id') id: String;
    @Output('delete') deleteEvent = new EventEmitter();
    @Output('item-selected') itemSelectedEvent = new EventEmitter();

    constructor() { }

    ngOnInit() { }

    onTitleSelected() {

    }

    onDelete() {
        // raise an event for handling delete
        this.deleteEvent.emit({
            id: this.id
        });
    }

    onItemSelected() {
        // raise an event for handling item selection
        this.itemSelectedEvent.emit({
            id: this.id
        });
    }
}


ngOnInit() { }


onTitleSelected() {

    }


onDelete() {
        // raise an event for handling delete
        this.deleteEvent.emit({
            id: this.id
        });
    }


onItemSelected() {
        // raise an event for handling item selection
        this.itemSelectedEvent.emit({
            id: this.id
        });
    }


(response: Response) => response.json()


response => {
      console.log("followSelectedUser response captured");
      console.log(response);
      var index = 0;
      this.usersData.forEach(user => {
        if(user==selecteduser){
          this.usersData[index].isFollowing = true;
        }
        index++;
      });

    }


user => {
        if(user==selecteduser){
          this.usersData[index].isFollowing = true;
        }
        index++;
      }


response => {
    this.usersData = response.result;
    this.currentUser = response.user[0];

    this.getFollowingStatus();

  }


user => {
      if(user.picture){
        this.usersData[index].imgUrl = "assets/icon/"+user.first_name.toLowerCase()+".jpg";
      }else{
        this.usersData[index].imgUrl = "assets/icon/avatar.jpeg";
      }

      followings.forEach(following => {
        this.usersData[index].followText = "Follow";
        if(user.emp_id==following.emp_id){
          this.usersData[index].followText = "Following";

        }
      });
      index++;
    }


following => {
        this.usersData[index].followText = "Follow";
        if(user.emp_id==following.emp_id){
          this.usersData[index].followText = "Following";

        }
      }


() => { location.href='/notifications' }


() => { location.href='/' }


(event) => { this.handleChange(event);}


user =>
                <div>

                  <ion-item>

                <ion-avatar


() => { this.followSelectedUser(user); }


() => { location.href='/notes/'+user.emp_id.$numberInt }


@Component({
  tag: 'app-home',
  styleUrl: 'app-home.css'
})
export class AppHome {
  @State() value: string;
  @State() showData: boolean;
  @State() usersData : any;
  @State() user_id = 10046;
  @State() currentUser :any;
  @State() searchQuery :string;

  @Prop() searchText:string;

  handleChange(event) {
    this.searchQuery = event.target.value;
    this.getUsersData(this.searchQuery);
  }
  showSelectedUserCard(selecteduser) {
    console.log("showSelectedUserCard called");
    this.getUsersData(selecteduser.first_name);
  }

  prepareNotes() {
    console.log("prepareNotes called");
  }

  followSelectedUser(selecteduser) {
    console.log('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/follow?action=follow&user='+this.user_id+'&follow='+selecteduser.emp_id.$numberInt);
    console.log("followSelectedUser called");
    fetch('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/follow?action=follow&user='+this.user_id+'&follow='+selecteduser.emp_id.$numberInt)
    .then((response: Response) => response.json())
    .then(response => {
      console.log("followSelectedUser response captured");
      console.log(response);
      var index = 0;
      this.usersData.forEach(user => {
        if(user==selecteduser){
          this.usersData[index].isFollowing = true;
        }
        index++;
      });

    });

  }

  getUsersData(searchText) {
console.log("printing serachtext before api call");
  fetch('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/get-profiles?user=10046&arg='+searchText)
  .then((response: Response) => response.json())
  .then(response => {
    this.usersData = response.result;
    this.currentUser = response.user[0];

    this.getFollowingStatus();

  });
  }

  getFollowingStatus() {
    console.log("getFollowingStatus called");
    var index = 0;
    var followings = this.currentUser.followers;
    console.log("current user in getFollowingStatus"+ this.currentUser);
    this.usersData.forEach(user => {
      if(user.picture){
        this.usersData[index].imgUrl = "assets/icon/"+user.first_name.toLowerCase()+".jpg";
      }else{
        this.usersData[index].imgUrl = "assets/icon/avatar.jpeg";
      }

      followings.forEach(following => {
        this.usersData[index].followText = "Follow";
        if(user.emp_id==following.emp_id){
          this.usersData[index].followText = "Following";

        }
      });
      index++;
    });
    this.showData = true;

  }

  componentWillLoad() {
    if(!this.searchText){
      this.searchText= "";
    }
    this.searchQuery = this.searchText;

    console.log("printing serachtext before api call componentWillLoad"+this.searchText);
    this.getUsersData(this.searchQuery);
  }

  render() {
    if(this.showData){
      return (

                <ion-item>
                <ion-label></ion-label>
                </ion-item>
              <ion-toolbar color="primary">

                <ion-buttons slot="primary">

                  <ion-button on-click={() => { location.href='/notifications' }}>
                    <ion-icon slot="icon-only" name="notifications" size="small" />
                  </ion-button>
                  <ion-button>
                    <ion-icon slot="icon-only" name="star" size="small" />
                  </ion-button>
                  <ion-button>
                    <ion-icon slot="icon-only" name="settings" size="small" />
                  </ion-button>
                </ion-buttons>
                <ion-title>Nasdaq Polly</ion-title>
                <ion-button on-click={() => { location.href='/' }}>
                    <ion-icon slot="icon-only" name="home" size="small" />
                  </ion-button>
              </ion-toolbar>

              <ion-searchbar on-change={(event) => { this.handleChange(event);}} on-input={(event) => { this.handleChange(event);}} value={this.searchQuery}></ion-searchbar>
              <ion-list>

                {this.usersData.map(user =>

                  <ion-item>

                <ion-avatar slot="start">

                </ion-avatar>

                <ion-label on-click={() => { this.showSelectedUserCard(user); }}>{user.first_name} {user.last_name}</ion-label>

              </ion-item>
                <ion-card hidden={!(user==this.usersData[0])}>
                <ion-card-header>
                  <ion-card-subtitle>{user.first_name} {user.last_name}</ion-card-subtitle>
                  <ion-card-title>{user.designation}</ion-card-title>

                </ion-card-header>

                <ion-card-content>
                  Keep close to Nature's heart... and break clear away, once in awhile,
                  and climb a mountain or spend a week in the woods. Wash your spirit clean.
            </ion-card-content>
                <ion-item>
                  <ion-icon name="pin" slot="start" />
                <ion-label>Checkedin at {user.city}</ion-label>
                </ion-item>
                <ion-item>
                  <ion-icon name="alarm" slot="start" />
                <ion-label>{user.last_checkin}</ion-label>
                </ion-item>
                <ion-item>
                <ion-button color="secondary" size="small" on-click={() => { this.followSelectedUser(user); }}>{user.followText}</ion-button>
                <ion-button color="secondary" size="small" on-click={() => { location.href='/notes/'+user.emp_id.$numberInt }}>Notes</ion-button>
                </ion-item>

              </ion-card>

                              )}


handleChange(event) {
    this.searchQuery = event.target.value;
    this.getUsersData(this.searchQuery);
  }


showSelectedUserCard(selecteduser) {
    console.log("showSelectedUserCard called");
    this.getUsersData(selecteduser.first_name);
  }


prepareNotes() {
    console.log("prepareNotes called");
  }


followSelectedUser(selecteduser) {
    console.log('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/follow?action=follow&user='+this.user_id+'&follow='+selecteduser.emp_id.$numberInt);
    console.log("followSelectedUser called");
    fetch('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/follow?action=follow&user='+this.user_id+'&follow='+selecteduser.emp_id.$numberInt)
    .then((response: Response) => response.json())
    .then(response => {
      console.log("followSelectedUser response captured");
      console.log(response);
      var index = 0;
      this.usersData.forEach(user => {
        if(user==selecteduser){
          this.usersData[index].isFollowing = true;
        }
        index++;
      });

    });

  }


getUsersData(searchText) {
console.log("printing serachtext before api call");
  fetch('https://webhooks.mongodb-stitch.com/api/client/v2.0/app/nasdaq-polly-lqprf/service/profiles-service/incoming_webhook/get-profiles?user=10046&arg='+searchText)
  .then((response: Response) => response.json())
  .then(response => {
    this.usersData = response.result;
    this.currentUser = response.user[0];

    this.getFollowingStatus();

  });
  }


getFollowingStatus() {
    console.log("getFollowingStatus called");
    var index = 0;
    var followings = this.currentUser.followers;
    console.log("current user in getFollowingStatus"+ this.currentUser);
    this.usersData.forEach(user => {
      if(user.picture){
        this.usersData[index].imgUrl = "assets/icon/"+user.first_name.toLowerCase()+".jpg";
      }else{
        this.usersData[index].imgUrl = "assets/icon/avatar.jpeg";
      }

      followings.forEach(following => {
        this.usersData[index].followText = "Follow";
        if(user.emp_id==following.emp_id){
          this.usersData[index].followText = "Following";

        }
      });
      index++;
    });
    this.showData = true;

  }


componentWillLoad() {
    if(!this.searchText){
      this.searchText= "";
    }
    this.searchQuery = this.searchText;

    console.log("printing serachtext before api call componentWillLoad"+this.searchText);
    this.getUsersData(this.searchQuery);
  }


render() {
    if(this.showData){
      return (

                <ion-item>
                <ion-label></ion-label>
                </ion-item>
              <ion-toolbar color="primary">

                <ion-buttons slot="primary">

                  <ion-button on-click={() => { location.href='/notifications' }}>
                    <ion-icon slot="icon-only" name="notifications" size="small" />
                  </ion-button>
                  <ion-button>
                    <ion-icon slot="icon-only" name="star" size="small" />
                  </ion-button>
                  <ion-button>
                    <ion-icon slot="icon-only" name="settings" size="small" />
                  </ion-button>
                </ion-buttons>
                <ion-title>Nasdaq Polly</ion-title>
                <ion-button on-click={() => { location.href='/' }}>
                    <ion-icon slot="icon-only" name="home" size="small" />
                  </ion-button>
              </ion-toolbar>

              <ion-searchbar on-change={(event) => { this.handleChange(event);}} on-input={(event) => { this.handleChange(event);}} value={this.searchQuery}></ion-searchbar>
              <ion-list>

                {this.usersData.map(user =>

                  <ion-item>

                <ion-avatar slot="start">

                </ion-avatar>

                <ion-label on-click={() => { this.showSelectedUserCard(user); }}>{user.first_name} {user.last_name}</ion-label>

              </ion-item>
                <ion-card hidden={!(user==this.usersData[0])}>
                <ion-card-header>
                  <ion-card-subtitle>{user.first_name} {user.last_name}</ion-card-subtitle>
                  <ion-card-title>{user.designation}</ion-card-title>

                </ion-card-header>

                <ion-card-content>
                  Keep close to Nature's heart... and break clear away, once in awhile,
                  and climb a mountain or spend a week in the woods. Wash your spirit clean.
            </ion-card-content>
                <ion-item>
                  <ion-icon name="pin" slot="start" />
                <ion-label>Checkedin at {user.city}</ion-label>
                </ion-item>
                <ion-item>
                  <ion-icon name="alarm" slot="start" />
                <ion-label>{user.last_checkin}</ion-label>
                </ion-item>
                <ion-item>
                <ion-button color="secondary" size="small" on-click={() => { this.followSelectedUser(user); }}>{user.followText}</ion-button>
                <ion-button color="secondary" size="small" on-click={() => { location.href='/notes/'+user.emp_id.$numberInt }}>Notes</ion-button>
                </ion-item>

              </ion-card>

                              )}


export function f1() {
    return new mExported.me.class1();
}


function f2() {
    return new mExported.me.class1();
}


export function f3() {
    return new mNonExported.mne.class1();
}


function f4() {
    return new mNonExported.mne.class1();
}


export class class1 extends mExported.me.class1 {
}


class class2 extends mExported.me.class1 {
}


export class class3 extends mNonExported.mne.class1 {
}


class class4 extends mNonExported.mne.class1 {
}


@Module({
  controllers: [ApiController, AppController],
  providers: [AppService, BaseService, ServiceA, ServiceB],
  imports: [UsersModule],
})
export class AppModule { }


function useFullScreenEditorTogglingEffect(fullscreen: boolean) {
  const globals = useGlobals();
  useLayoutEffect(() => {
    if (!fullscreen) {
      iframeFullscreenContainer(globals.id, dependencies__.all.body()).classList.add("hidden");
    } else {
      iframeFullscreenContainer(globals.id, dependencies__.all.body()).classList.remove("hidden");
    }
  }, [fullscreen]);
}


export function SingleEditorApp(props: {
  openFileExtension: string;
  readonly: boolean;
  getFileName: () => string;
  getFileContents: () => Promise<string | undefined>;
  toolbarContainer: HTMLElement;
  iframeContainer: HTMLElement;
  githubTextEditorToReplace: HTMLElement;
  fileInfo: FileInfo;
}) {
  const [textMode, setTextMode] = useState(false);
  const [textModeEnabled, setTextModeEnabled] = useState(false);
  const [fullscreen, setFullscreen] = useState(false);
  const globals = useGlobals();
  const isolatedEditorRef = useRef<IsolatedEditorRef>(null);

  useFullScreenEditorTogglingEffect(fullscreen);
  useIsolatedEditorTogglingEffect(textMode, props.iframeContainer, props.githubTextEditorToReplace);

  const IsolatedEditorComponent = (
    <IsolatedEditor
      getFileContents={props.getFileContents}
      contentPath={props.fileInfo.path}
      openFileExtension={props.openFileExtension}
      textMode={textMode}
      readonly={props.readonly}
      keepRenderedEditorInTextMode={true}
      ref={isolatedEditorRef}
    />
  );

  const exitFullScreen = useCallback(() => {
    setFullscreen(false);
    setTextModeEnabled(false);
  }, []);

  const deactivateTextMode = useCallback(() => setTextMode(false), []);
  const activateTextMode = useCallback(() => setTextMode(true), []);
  const goFullScreen = useCallback(() => setFullscreen(true), []);

  const openExternalEditor = () => {
    props.getFileContents().then(fileContent => {
      globals.externalEditorManager?.open(props.getFileName(), fileContent!, props.readonly);
    });
  };

  const linkToExternalEditor = useMemo(() => {
    return globals.externalEditorManager?.getLink(
      `${props.fileInfo.org}/${props.fileInfo.repo}/${props.fileInfo.gitRef}/${props.fileInfo.path}`
    );
  }, [globals.externalEditorManager]);

  useEffect(() => {
    const listener = globals.externalEditorManager?.listenToComeBack(fileName => {
      dependencies__.all.edit__githubFileNameInput()!.value = fileName;
    }, isolatedEditorRef.current?.setContent!);

    return () => {
      listener?.stopListening();
    };
  }, [globals.externalEditorManager]);

  return (
    <>
      <IsolatedEditorContext.Provider
        value={{
          onEditorReady: () => setTextModeEnabled(true),
          fullscreen: fullscreen,
          textMode: textMode,
          repoInfo: {
            gitref: props.fileInfo.gitRef,
            owner: props.fileInfo.org,
            repo: props.fileInfo.repo
          }
        }}


() => {
    if (!fullscreen) {
      iframeFullscreenContainer(globals.id, dependencies__.all.body()).classList.add("hidden");
    } else {
      iframeFullscreenContainer(globals.id, dependencies__.all.body()).classList.remove("hidden");
    }
  }


() => {
    setFullscreen(false);
    setTextModeEnabled(false);
  }


() => setTextMode(false)


() => setTextMode(true)


() => setFullscreen(true)


() => {
    props.getFileContents().then(fileContent => {
      globals.externalEditorManager?.open(props.getFileName(), fileContent!, props.readonly);
    });
  }


fileContent => {
      globals.externalEditorManager?.open(props.getFileName(), fileContent!, props.readonly);
    }


() => {
    return globals.externalEditorManager?.getLink(
      `${props.fileInfo.org}/${props.fileInfo.repo}/${props.fileInfo.gitRef}/${props.fileInfo.path}`
    );
  }


() => {
    const listener = globals.externalEditorManager?.listenToComeBack(fileName => {
      dependencies__.all.edit__githubFileNameInput()!.value = fileName;
    }, isolatedEditorRef.current?.setContent!);

    return () => {
      listener?.stopListening();
    };
  }


fileName => {
      dependencies__.all.edit__githubFileNameInput()!.value = fileName;
    }


() => {
      listener?.stopListening();
    }


() => setTextModeEnabled(true)


(
    props: DefaultSidePanelProps
): JSX.Element => {
    const { onSidePanelItemClick } = props;
    return (
        <SidePanelItems type="desktop" onSidePanelItemClick={ onSidePanelItemClick }/>


(props: MobileSidePanelProps): JSX.Element => {
    const { children, onPusherClick, visible, onSidePanelItemClick } = props;
    return (
        <Sidebar.Pushable>
            <Sidebar
                animation="push"
                visible={ visible }
            >
                <SidePanelItems type="mobile" onSidePanelItemClick={ onSidePanelItemClick }/>
            </Sidebar>
            <Sidebar.Pusher
                onClick={ onPusherClick }
                className="side-panel-pusher"
            >
                { children }
            </Sidebar.Pusher>
        </Sidebar.Pushable>


(props: SidePanelItemsProps): JSX.Element => {
    const { type, onSidePanelItemClick } = props;
    const activeRoute = (path: string) => {
        const pathname = window.location.pathname;
        const urlTokens = path.split("/");
        return pathname.indexOf(urlTokens[1]) > -1 ? "active" : "";
    };
    return (
        <Menu className={ `side-panel ${ type }` }


(path: string) => {
        const pathname = window.location.pathname;
        const urlTokens = path.split("/");
        return pathname.indexOf(urlTokens[1]) > -1 ? "active" : "";
    }


(route, index) => (
                    route.showOnSidePanel ?
                        <Menu.Item
                            as={ NavLink }


(
    props: SidePanelWrapperProps
): JSX.Element => {
    const { mobileSidePanelVisibility, children, onSidePanelPusherClick, onSidePanelItemClick } = props;
    return (
        <>
            <Responsive { ...Responsive.onlyMobile }>
                <MobileSidePanel
                    onPusherClick={ onSidePanelPusherClick }
                    visible={ mobileSidePanelVisibility }
                    onSidePanelItemClick={ onSidePanelItemClick }
                >
                    <Divider className="x1" hidden/>
                    <Container>{ children }</Container>
                </MobileSidePanel>
            </Responsive>
            <Responsive as={ Container } minWidth={ Responsive.onlyTablet.minWidth }>
                <Divider className="x2" hidden/>
                <Grid>
                    <Grid.Row columns={ 2 }>
                        <Grid.Column tablet={ 6 } computer={ 4 }>
                            <DefaultSidePanel onSidePanelItemClick={ onSidePanelItemClick }/>
                        </Grid.Column>
                        <Grid.Column tablet={ 10 } computer={ 12 }>
                            { children }
                        </Grid.Column>.
                    </Grid.Row>
                </Grid>
            </Responsive>
        </>


/**
 * Default side panel component Prop types.
 */
interface DefaultSidePanelProps {
    onSidePanelItemClick: () => void;
}


/**
 * Mobile side panel component Prop types.
 */
interface MobileSidePanelProps extends DefaultSidePanelProps {
    children?: React.ReactNode;
    onPusherClick: () => void;
    visible: boolean;
}


/**
 * Side panel items component Prop types.
 */
interface SidePanelItemsProps {
    onSidePanelItemClick: () => void;
    type: "desktop" | "mobile";
}


/**
 * Side panel wrapper component Prop types.
 */
interface SidePanelWrapperProps {
    children?: React.ReactNode;
    onSidePanelItemClick: () => void;
    onSidePanelPusherClick: () => void;
    mobileSidePanelVisibility: boolean;
}


activeRoute(route


interface SvgrComponent extends React.FC<React.SVGAttributes<SVGElement>> {}


@Component({
    selector: 'ngx-contract',
    styleUrls: ['./delete-customer.scss'],
    template: `
        <nb-card>
            <nb-card-header>
                {{ title }}

                    ×

            </nb-card-header>
            <nb-card-body>

Do you want to delete id {{ this.id }}

                    <button class="float-right btn btn-info" (click)="delete()">OK</button>
                    <button class="float-right  btn btn-hint" (click)="dismiss()">Cancel</button>

            </nb-card-body>
        </nb-card>
    `,
})
export class DeleteComponent implements OnInit {
    id: String;
    title: String;
    constructor(protected ref: NbDialogRef<DeleteComponent>, private contractService: ContractService) {}
    ngOnInit() {}
    dismiss() {
        this.ref.close();
    }
    async delete() {
        let i = this.contractService.delete(this.id);
    }
}


dismiss() {
        this.ref.close();
    }


async delete() {
        let i = this.contractService.delete(this.id);
    }


function isNode() {
  if (typeof process === 'object') {
    if (typeof process.versions === 'object') {
      if (typeof process.versions.node !== 'undefined') {
        return true;
      }
    }
  }
  return false;
}


function isUint8Array(object: any) {
  return object instanceof Uint8Array && (!isNode() || !Buffer.isBuffer(object));
}


function isArrayBuffer(object: any) {
  return object instanceof ArrayBuffer;
}


function isBuffer(object: any) {
  if (!isNode()) {
    return false;
  }
  return Buffer.isBuffer(object);
}


export function uncompress(compressed: Buffer): Buffer;


export function uncompress(compressed: Uint8Array): Uint8Array;


export function uncompress(compressed: ArrayBuffer): ArrayBuffer;


export function uncompress(compressed: any) {
  if (!isUint8Array(compressed) && !isArrayBuffer(compressed) && !isBuffer(compressed)) {
    throw new TypeError(TYPE_ERROR_MSG);
  }
  let uint8Mode = false;
  let arrayBufferMode = false;
  let buffer: Buffer;
  if (isUint8Array(compressed)) {
    uint8Mode = true;
    buffer = Buffer.from(compressed.buffer, compressed.byteOffset, compressed.byteLength);
  } else if (isArrayBuffer(compressed)) {
    arrayBufferMode = true;
    buffer = Buffer.from(compressed);
  } else {
    buffer = compressed;
  }

  const length = readUncompressedLength(buffer);
  if (length === -1) throw new Error('Invalid Snappy bitstream');
  const target: Buffer = Buffer.alloc(length);

  if (!uncompressToBuffer(buffer, target)) {
    throw new Error('Invalid Snappy bitstream');
  }

  if (uint8Mode) {
    return new Uint8Array(target.buffer);
  } else if (arrayBufferMode) {
    return target.buffer;
  } else {
    return target;
  }
}


export function compress(uncompressed: Buffer): Buffer;


export function compress(uncompressed: Uint8Array): Uint8Array;


export function compress(uncompressed: ArrayBuffer): ArrayBuffer;


export function compress(uncompressed: any) {
  if (!isUint8Array(uncompressed) && !isArrayBuffer(uncompressed) && !isBuffer(uncompressed)) {
    throw new TypeError(TYPE_ERROR_MSG);
  }
  let uint8Mode = false;
  let arrayBufferMode = false;
  let buffer: Buffer;
  if (isUint8Array(uncompressed)) {
    uint8Mode = true;
    buffer = Buffer.from(uncompressed.buffer, uncompressed.byteOffset, uncompressed.byteLength);
  } else if (isArrayBuffer(uncompressed)) {
    arrayBufferMode = true;
    buffer = Buffer.from(uncompressed);
  } else {
    buffer = uncompressed;
  }

  const maxLength = maxCompressedLength(buffer);
  const target: Buffer = Buffer.alloc(maxLength);
  const length = compressToBuffer(buffer, target);
  const array = target.buffer.slice(0, length);

  if (uint8Mode) {
    return new Uint8Array(array);
  } else if (arrayBufferMode) {
    return array;
  } else {
    return Buffer.from(array);
  }
}


() => {
  let junoClient: JunoClient;
  let gitHubOAuthService: GitHubOAuthService;
  let originalDataExplorer: Explorer;

  beforeEach(() => {
    junoClient = new JunoClient();
    gitHubOAuthService = new GitHubOAuthService(junoClient);
    originalDataExplorer = window.dataExplorer;
    window.dataExplorer = {
      ...originalDataExplorer,
    } as Explorer;
    window.dataExplorer.notebookManager = new NotebookManager();
    window.dataExplorer.notebookManager.junoClient = junoClient;
    window.dataExplorer.notebookManager.gitHubOAuthService = gitHubOAuthService;
  });

  afterEach(() => {
    jest.resetAllMocks();
    window.dataExplorer = originalDataExplorer;
    originalDataExplorer = undefined;
    gitHubOAuthService = undefined;
    junoClient = undefined;
  });

  it("logout deletes app authorization and resets token", async () => {
    const deleteAppAuthorizationCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NoContent });
    junoClient.deleteAppAuthorization = deleteAppAuthorizationCallback;

    await gitHubOAuthService.logout();
    expect(deleteAppAuthorizationCallback).toBeCalled();
    expect(gitHubOAuthService.getTokenObservable()()).toBeUndefined();
  });

  it("resetToken resets token", () => {
    gitHubOAuthService.resetToken();
    expect(gitHubOAuthService.getTokenObservable()()).toBeUndefined();
  });

  it("startOAuth resets OAuth state", async () => {
    let url: string;
    const windowOpenCallback = jest.fn().mockImplementation((value: string) => {
      url = value;
    });
    window.open = windowOpenCallback;

    await gitHubOAuthService.startOAuth("scope");
    expect(windowOpenCallback).toBeCalled();

    const initialParams = new URLSearchParams(new URL(url).search);
    expect(initialParams.get("state")).toBeDefined();

    await gitHubOAuthService.startOAuth("another scope");
    expect(windowOpenCallback).toBeCalled();

    const newParams = new URLSearchParams(new URL(url).search);
    expect(newParams.get("state")).toBeDefined();
    expect(newParams.get("state")).not.toEqual(initialParams.get("state"));
  });

  it("finishOAuth updates token", async () => {
    const data = { key: "value" };
    const getGitHubTokenCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.OK, data });
    junoClient.getGitHubToken = getGitHubTokenCallback;

    const initialToken = gitHubOAuthService.getTokenObservable()();
    const state = await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state,
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);
    const updatedToken = gitHubOAuthService.getTokenObservable()();

    expect(getGitHubTokenCallback).toBeCalledWith("code");
    expect(initialToken).not.toEqual(updatedToken);
  });

  it("finishOAuth updates token to error if state doesn't match", async () => {
    await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state: "state",
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);

    expect(gitHubOAuthService.getTokenObservable()().error).toBeDefined();
  });

  it("finishOAuth updates token to error if unable to fetch token", async () => {
    const getGitHubTokenCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NotFound });
    junoClient.getGitHubToken = getGitHubTokenCallback;

    const state = await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state,
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);

    expect(getGitHubTokenCallback).toBeCalledWith("code");
    expect(gitHubOAuthService.getTokenObservable()().error).toBeDefined();
  });

  it("isLoggedIn returns false if resetToken is called", () => {
    gitHubOAuthService.resetToken();
    expect(gitHubOAuthService.isLoggedIn()).toBeFalsy();
  });

  it("isLoggedIn returns false if logout is called", async () => {
    const deleteAppAuthorizationCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NoContent });
    junoClient.deleteAppAuthorization = deleteAppAuthorizationCallback;

    await gitHubOAuthService.logout();
    expect(gitHubOAuthService.isLoggedIn()).toBeFalsy();
  });
}


() => {
    junoClient = new JunoClient();
    gitHubOAuthService = new GitHubOAuthService(junoClient);
    originalDataExplorer = window.dataExplorer;
    window.dataExplorer = {
      ...originalDataExplorer,
    } as Explorer;
    window.dataExplorer.notebookManager = new NotebookManager();
    window.dataExplorer.notebookManager.junoClient = junoClient;
    window.dataExplorer.notebookManager.gitHubOAuthService = gitHubOAuthService;
  }


() => {
    jest.resetAllMocks();
    window.dataExplorer = originalDataExplorer;
    originalDataExplorer = undefined;
    gitHubOAuthService = undefined;
    junoClient = undefined;
  }


async () => {
    const deleteAppAuthorizationCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NoContent });
    junoClient.deleteAppAuthorization = deleteAppAuthorizationCallback;

    await gitHubOAuthService.logout();
    expect(deleteAppAuthorizationCallback).toBeCalled();
    expect(gitHubOAuthService.getTokenObservable()()).toBeUndefined();
  }


() => {
    gitHubOAuthService.resetToken();
    expect(gitHubOAuthService.getTokenObservable()()).toBeUndefined();
  }


async () => {
    let url: string;
    const windowOpenCallback = jest.fn().mockImplementation((value: string) => {
      url = value;
    });
    window.open = windowOpenCallback;

    await gitHubOAuthService.startOAuth("scope");
    expect(windowOpenCallback).toBeCalled();

    const initialParams = new URLSearchParams(new URL(url).search);
    expect(initialParams.get("state")).toBeDefined();

    await gitHubOAuthService.startOAuth("another scope");
    expect(windowOpenCallback).toBeCalled();

    const newParams = new URLSearchParams(new URL(url).search);
    expect(newParams.get("state")).toBeDefined();
    expect(newParams.get("state")).not.toEqual(initialParams.get("state"));
  }


(value: string) => {
      url = value;
    }


async () => {
    const data = { key: "value" };
    const getGitHubTokenCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.OK, data });
    junoClient.getGitHubToken = getGitHubTokenCallback;

    const initialToken = gitHubOAuthService.getTokenObservable()();
    const state = await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state,
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);
    const updatedToken = gitHubOAuthService.getTokenObservable()();

    expect(getGitHubTokenCallback).toBeCalledWith("code");
    expect(initialToken).not.toEqual(updatedToken);
  }


async () => {
    await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state: "state",
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);

    expect(gitHubOAuthService.getTokenObservable()().error).toBeDefined();
  }


async () => {
    const getGitHubTokenCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NotFound });
    junoClient.getGitHubToken = getGitHubTokenCallback;

    const state = await gitHubOAuthService.startOAuth("scope");

    const params: IGitHubConnectorParams = {
      state,
      code: "code",
    };
    await gitHubOAuthService.finishOAuth(params);

    expect(getGitHubTokenCallback).toBeCalledWith("code");
    expect(gitHubOAuthService.getTokenObservable()().error).toBeDefined();
  }


() => {
    gitHubOAuthService.resetToken();
    expect(gitHubOAuthService.isLoggedIn()).toBeFalsy();
  }


async () => {
    const deleteAppAuthorizationCallback = jest.fn().mockReturnValue({ status: HttpStatusCodes.NoContent });
    junoClient.deleteAppAuthorization = deleteAppAuthorizationCallback;

    await gitHubOAuthService.logout();
    expect(gitHubOAuthService.isLoggedIn()).toBeFalsy();
  }


(lang) => {
            this.language = lang;
        }


(result) => {
            this.needCaptcha = result.isCaptchaNeed;
            this.publicKey = result.publicKey;
        }


(config) => {
            this.socialConfig = config && config.social;
        }


(config: any) => {
                this.makePasswordSettings(config);
            }


() => this.makePasswordSettings()


(r) => {
                    if (r === 'accept') {
                        this.registration();
                    }
                }


(err) => {
                    console.info(err);
                }


(key) => {
            this.registerAccount.langKey = key;
            this.makeLogins();
            this.registerService.save(this.registerAccount).subscribe(() => {
                    this.success = true;
                    this.eventManager.broadcast({name: XM_EVENT_LIST.XM_REGISTRATION, content: ''});
                },
                (response) => this.processError(response));
        }


() => {
                    this.success = true;
                    this.eventManager.broadcast({name: XM_EVENT_LIST.XM_REGISTRATION, content: ''});
                }


(response) => this.processError(response)


(result) => {
                this.publicKey = result.publicKey;
            }