deno.land / std@0.201.0 / path / _extname.ts

نووسراو ببینە
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
// Copyright 2018-2023 the Deno authors. All rights reserved. MIT license.// This module is browser compatible.
import { CHAR_COLON, CHAR_DOT } from "./_constants.ts";import { assertPath, isPathSeparator, isPosixPathSeparator, isWindowsDeviceRoot,} from "./_util.ts";
/** * Return the extension of the `path` with leading period. * @param path with extension * @returns extension (ex. for `file.ts` returns `.ts`) */export function posixExtname(path: string): string { assertPath(path);
let startDot = -1; let startPart = 0; let end = -1; let matchedSlash = true; // Track the state of characters (if any) we see before our first dot and // after any path separator we find let preDotState = 0; for (let i = path.length - 1; i >= 0; --i) { const code = path.charCodeAt(i); if (isPosixPathSeparator(code)) { // If we reached a path separator that was not part of a set of path // separators at the end of the string, stop now if (!matchedSlash) { startPart = i + 1; break; } continue; } if (end === -1) { // We saw the first non-path separator, mark this as the end of our // extension matchedSlash = false; end = i + 1; } if (code === CHAR_DOT) { // If this is our first dot, mark it as the start of our extension if (startDot === -1) startDot = i; else if (preDotState !== 1) preDotState = 1; } else if (startDot !== -1) { // We saw a non-dot and non-path separator before our dot, so we should // have a good chance at having a non-empty extension preDotState = -1; } }
if ( startDot === -1 || end === -1 || // We saw a non-dot character immediately before the dot preDotState === 0 || // The (right-most) trimmed path component is exactly '..' (preDotState === 1 && startDot === end - 1 && startDot === startPart + 1) ) { return ""; } return path.slice(startDot, end);}
/** * Return the extension of the `path` with leading period. * @param path with extension * @returns extension (ex. for `file.ts` returns `.ts`) */export function windowsExtname(path: string): string { assertPath(path);
let start = 0; let startDot = -1; let startPart = 0; let end = -1; let matchedSlash = true; // Track the state of characters (if any) we see before our first dot and // after any path separator we find let preDotState = 0;
// Check for a drive letter prefix so as not to mistake the following // path separator as an extra separator at the end of the path that can be // disregarded
if ( path.length >= 2 && path.charCodeAt(1) === CHAR_COLON && isWindowsDeviceRoot(path.charCodeAt(0)) ) { start = startPart = 2; }
for (let i = path.length - 1; i >= start; --i) { const code = path.charCodeAt(i); if (isPathSeparator(code)) { // If we reached a path separator that was not part of a set of path // separators at the end of the string, stop now if (!matchedSlash) { startPart = i + 1; break; } continue; } if (end === -1) { // We saw the first non-path separator, mark this as the end of our // extension matchedSlash = false; end = i + 1; } if (code === CHAR_DOT) { // If this is our first dot, mark it as the start of our extension if (startDot === -1) startDot = i; else if (preDotState !== 1) preDotState = 1; } else if (startDot !== -1) { // We saw a non-dot and non-path separator before our dot, so we should // have a good chance at having a non-empty extension preDotState = -1; } }
if ( startDot === -1 || end === -1 || // We saw a non-dot character immediately before the dot preDotState === 0 || // The (right-most) trimmed path component is exactly '..' (preDotState === 1 && startDot === end - 1 && startDot === startPart + 1) ) { return ""; } return path.slice(startDot, end);}
std

Version Info

Tagged at
2 years ago