Skip to content

Commit 610beeb

Browse files
author
thebarada
committed
feat(cookies) separate browser and server logic to appropriate modules
1 parent 80d0eb8 commit 610beeb

11 files changed

+145
-111
lines changed

browser.ts

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export * from './src/browser';

index.ts

-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
export * from './src/cookies.module';
21
export * from './src/cookies.service';
3-
export * from './src/cookies-node.service';
42
export * from './src/cookies-options.service';
53
export * from './src/cookies-options';

server.ts

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
export * from './src/server';

src/browser/browser-cookies.module.ts

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import { ModuleWithProviders, NgModule } from '@angular/core';
2+
3+
import { CookiesOptions } from '../cookies-options';
4+
import { COOKIES_OPTIONS, CookiesOptionsService } from '../cookies-options.service';
5+
import { CookiesService } from '../cookies.service';
6+
import { BrowserCookiesService } from './browser-cookies.service';
7+
8+
@NgModule()
9+
export class BrowserCookiesModule {
10+
static forRoot(options: CookiesOptions = {}): ModuleWithProviders {
11+
return {
12+
ngModule: BrowserCookiesModule,
13+
providers: [
14+
{provide: COOKIES_OPTIONS, useValue: options},
15+
CookiesOptionsService,
16+
{provide: CookiesService, useClass: BrowserCookiesService}
17+
]
18+
};
19+
}
20+
}
+73
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
import { Injectable } from '@angular/core';
2+
3+
import { CookiesService } from '../cookies.service';
4+
import { CookiesOptions } from '../cookies-options';
5+
import { CookiesOptionsService } from '../cookies-options.service';
6+
import { isBlank, isString, mergeOptions, safeDecodeURIComponent } from '../utils';
7+
8+
@Injectable()
9+
export class BrowserCookiesService extends CookiesService {
10+
get cookieString(): string {
11+
return document.cookie || '';
12+
}
13+
14+
set cookieString(val: string) {
15+
document.cookie = val;
16+
}
17+
18+
constructor(cookiesOptions: CookiesOptionsService) {
19+
super(cookiesOptions);
20+
}
21+
22+
protected cookiesReader(): { [key: string]: any } {
23+
let lastCookies = {};
24+
let lastCookieString = '';
25+
let cookiesArray: string[], cookie: string, i: number, index: number, name: string;
26+
let currentCookieString = this.cookieString;
27+
if (currentCookieString !== lastCookieString) {
28+
lastCookieString = currentCookieString;
29+
cookiesArray = lastCookieString.split('; ');
30+
lastCookies = {};
31+
for (i = 0; i < cookiesArray.length; i++) {
32+
cookie = cookiesArray[i];
33+
index = cookie.indexOf('=');
34+
if (index > 0) { // ignore nameless cookies
35+
name = safeDecodeURIComponent(cookie.substring(0, index));
36+
if (isBlank((<any>lastCookies)[name])) {
37+
(<any>lastCookies)[name] = safeDecodeURIComponent(cookie.substring(index + 1));
38+
}
39+
}
40+
}
41+
}
42+
return lastCookies;
43+
}
44+
45+
protected cookiesWriter(): (name: string, value: string | undefined, options?: CookiesOptions) => void {
46+
return (name: string, value: string | undefined, options?: CookiesOptions) => {
47+
this.cookieString = this.buildCookieString(name, value, options);
48+
};
49+
}
50+
51+
private buildCookieString(name: string, value: string | undefined, options?: CookiesOptions): string {
52+
let opts: CookiesOptions = mergeOptions(this.options, options);
53+
let expires: any = opts.expires;
54+
if (isBlank(value)) {
55+
expires = 'Thu, 01 Jan 1970 00:00:00 GMT';
56+
value = '';
57+
}
58+
if (isString(expires)) {
59+
expires = new Date(expires);
60+
}
61+
let str = encodeURIComponent(name) + '=' + encodeURIComponent((value as string));
62+
str += opts.path ? ';path=' + opts.path : '';
63+
str += opts.domain ? ';domain=' + opts.domain : '';
64+
str += expires ? ';expires=' + expires.toUTCString() : '';
65+
str += opts.secure ? ';secure' : '';
66+
let cookiesLength = str.length + 1;
67+
if (cookiesLength > 4096) {
68+
console.log(`Cookie \'${name}\' possibly not set or overflowed because it was too
69+
large (${cookiesLength} > 4096 bytes)!`);
70+
}
71+
return str;
72+
}
73+
}

src/browser/index.ts

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
export * from './browser-cookies.module';
2+
export * from './browser-cookies.service';

src/cookies.module.ts

-31
This file was deleted.

src/cookies.service.ts

+10-72
Original file line numberDiff line numberDiff line change
@@ -2,32 +2,22 @@ import { Injectable } from '@angular/core';
22

33
import { CookiesOptions } from './cookies-options';
44
import { CookiesOptionsService } from './cookies-options.service';
5-
import { isBlank, isString, mergeOptions, safeDecodeURIComponent, safeJsonParse } from './utils';
6-
7-
export interface ICookiesService {
8-
get(key: string): string;
9-
getObject(key: string): { [key: string]: string } | string;
10-
getAll(): { [key: string]: string };
11-
put(key: string, value: string, options?: CookiesOptions): void;
12-
putObject(key: string, value: { [key: string]: string }, options?: CookiesOptions): void;
13-
remove(key: string, options?: CookiesOptions): void;
14-
removeAll(): void;
15-
}
5+
import { safeJsonParse } from './utils';
166

177
@Injectable()
18-
export class CookiesService implements ICookiesService {
8+
export class CookiesService {
199
protected options: CookiesOptions;
2010

21-
get cookieString(): string {
22-
return document.cookie || '';
11+
constructor(cookiesOptions: CookiesOptionsService) {
12+
this.options = cookiesOptions.options;
2313
}
2414

25-
set cookieString(val: string) {
26-
document.cookie = val;
15+
put(key: string, value: string, options?: CookiesOptions): void {
16+
this.cookiesWriter()(key, value, options);
2717
}
2818

29-
constructor(cookiesOptions: CookiesOptionsService) {
30-
this.options = cookiesOptions.options;
19+
putObject(key: string, value: Object, options?: CookiesOptions): void {
20+
this.put(key, JSON.stringify(value), options);
3121
}
3222

3323
get(key: string): string {
@@ -43,14 +33,6 @@ export class CookiesService implements ICookiesService {
4333
return <any>this.cookiesReader();
4434
}
4535

46-
put(key: string, value: string, options?: CookiesOptions): void {
47-
this.cookiesWriter()(key, value, options);
48-
}
49-
50-
putObject(key: string, value: Object, options?: CookiesOptions): void {
51-
this.put(key, JSON.stringify(value), options);
52-
}
53-
5436
remove(key: string, options?: CookiesOptions): void {
5537
this.cookiesWriter()(key, undefined, options);
5638
}
@@ -63,54 +45,10 @@ export class CookiesService implements ICookiesService {
6345
}
6446

6547
protected cookiesReader(): { [key: string]: any } {
66-
let lastCookies = {};
67-
let lastCookieString = '';
68-
let cookiesArray: string[], cookie: string, i: number, index: number, name: string;
69-
let currentCookieString = this.cookieString;
70-
if (currentCookieString !== lastCookieString) {
71-
lastCookieString = currentCookieString;
72-
cookiesArray = lastCookieString.split('; ');
73-
lastCookies = {};
74-
for (i = 0; i < cookiesArray.length; i++) {
75-
cookie = cookiesArray[i];
76-
index = cookie.indexOf('=');
77-
if (index > 0) { // ignore nameless cookies
78-
name = safeDecodeURIComponent(cookie.substring(0, index));
79-
if (isBlank((<any>lastCookies)[name])) {
80-
(<any>lastCookies)[name] = safeDecodeURIComponent(cookie.substring(index + 1));
81-
}
82-
}
83-
}
84-
}
85-
return lastCookies;
48+
return { };
8649
}
8750

8851
protected cookiesWriter(): (name: string, value: string | undefined, options?: CookiesOptions) => void {
89-
return (name: string, value: string | undefined, options?: CookiesOptions) => {
90-
this.cookieString = this.buildCookieString(name, value, options);
91-
};
92-
}
93-
94-
private buildCookieString(name: string, value: string | undefined, options?: CookiesOptions): string {
95-
let opts: CookiesOptions = mergeOptions(this.options, options);
96-
let expires: any = opts.expires;
97-
if (isBlank(value)) {
98-
expires = 'Thu, 01 Jan 1970 00:00:00 GMT';
99-
value = '';
100-
}
101-
if (isString(expires)) {
102-
expires = new Date(expires);
103-
}
104-
let str = encodeURIComponent(name) + '=' + encodeURIComponent((value as string));
105-
str += opts.path ? ';path=' + opts.path : '';
106-
str += opts.domain ? ';domain=' + opts.domain : '';
107-
str += expires ? ';expires=' + expires.toUTCString() : '';
108-
str += opts.secure ? ';secure' : '';
109-
let cookiesLength = str.length + 1;
110-
if (cookiesLength > 4096) {
111-
console.log(`Cookie \'${name}\' possibly not set or overflowed because it was too
112-
large (${cookiesLength} > 4096 bytes)!`);
113-
}
114-
return str;
52+
return () => { };
11553
}
11654
}

src/server/index.ts

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
export * from './server-cookies.module';
2+
export * from './server-cookies.service';

src/server/server-cookies.module.ts

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import { ModuleWithProviders, NgModule } from '@angular/core';
2+
3+
import { CookiesOptions } from '../cookies-options';
4+
import { COOKIES_OPTIONS, CookiesOptionsService } from '../cookies-options.service';
5+
import { CookiesService } from '../cookies.service';
6+
import { ServerCookiesService } from './server-cookies.service';
7+
8+
@NgModule()
9+
export class ServerCookiesModule {
10+
static forRoot(options: CookiesOptions = {}): ModuleWithProviders {
11+
return {
12+
ngModule: ServerCookiesModule,
13+
providers: [
14+
{provide: COOKIES_OPTIONS, useValue: options},
15+
CookiesOptionsService,
16+
{provide: CookiesService, useClass: ServerCookiesService}
17+
]
18+
};
19+
}
20+
}

src/cookies-node.service.ts src/server/server-cookies.service.ts

+16-6
Original file line numberDiff line numberDiff line change
@@ -1,24 +1,34 @@
11
import { Inject, Injectable } from '@angular/core';
22

3-
import { CookiesService } from './cookies.service';
4-
import { CookiesOptionsService } from './cookies-options.service';
5-
import { CookiesOptions } from './cookies-options';
6-
import { isString, mergeOptions } from './utils';
3+
import { CookiesService } from '../cookies.service';
4+
import { CookiesOptionsService } from '../cookies-options.service';
5+
import { CookiesOptions } from '../cookies-options';
6+
import { isString, mergeOptions } from '../utils';
77

88
@Injectable()
9-
export class CookiesNodeService extends CookiesService {
9+
export class ServerCookiesService extends CookiesService {
10+
private newCookies: { [name: string]: string | undefined } = {};
11+
1012
constructor(cookiesOptions: CookiesOptionsService,
1113
@Inject('REQUEST') private request: any,
1214
@Inject('RESPONSE') private response: any) {
1315
super(cookiesOptions);
1416
}
1517

1618
protected cookiesReader(): { [key: string]: any } {
17-
return this.request.cookies;
19+
const allCookies: { [key: string]: any } = {...this.request.cookies, ...this.newCookies};
20+
const cookies: { [key: string]: any } = {};
21+
for (const name in allCookies) {
22+
if (typeof allCookies[name] !== 'undefined') {
23+
cookies[name] = allCookies[name];
24+
}
25+
}
26+
return cookies;
1827
}
1928

2029
protected cookiesWriter(): (name: string, value: string | undefined, options?: CookiesOptions) => void {
2130
return (name: string, value: string | undefined, options?: CookiesOptions) => {
31+
this.newCookies[name] = value;
2232
this.response.cookie(name, value, this.buildCookiesOptions(options));
2333
};
2434
}

0 commit comments

Comments
 (0)