In diesem Artikel finden Sie einige Interviewfragen zu Browsern. Sehen Sie, wie viele Sie beantworten können. Analysieren Sie die richtigen Antworten und sehen Sie, wie viele Sie richtig machen können!
Der Kernel des Browsers kann in zwei Teile unterteilt werden:
渲染引擎
和JS引擎
(Hinweis: Der Browser-Kernel, auf den wir uns oft beziehen, bezieht sich auf die Rendering-Engine)
Da die JS-Engine immer beliebter wird Unabhängig, der Kernel bezieht sich nur auf die Rendering-Engine. Die Rendering-Engine wird hauptsächlich verwendet, um Netzwerkseitenressourcen anzufordern, die analysiert und gesetzt und dem Benutzer präsentiert werden sollen
Browser/RunTime | Kernel (Rendering-Engine) | JavaScript-Engine |
---|---|---|
Chrome | Blink ( 28~) Webkit (Chrome 27) | V8 |
FireFox | Gecko | SpiderMonkey |
Safari | Webkit | JavaScriptCore |
Edge | EdgeHTML | Chakra (für JavaScript) |
IE | Trident | Chakra (für JScript) |
Opera | Presto->blink | Linear A (4.0-6.1) /Linear B (7.0 -9.2)/Futhark (9.5-10.2)/ Carakan (10.5-) |
Node.js | - | V8 |
Benutzeroberfläche: einschließlich Adressleiste, Vorwärts-/Zurück-/Aktualisierungs-/Lesezeichenschaltflächen usw.
Browser-Engine: überträgt Anweisungen zwischen der Benutzeroberfläche und der Rendering-Engine.
Rendering-Engine: wird zum Zeichnen von Anforderungsinhalten verwendet
Netzwerk: Wird zum Abschließen von Netzwerkaufrufen wie http-Anfragen verwendet, verfügt über eine plattformunabhängige Schnittstelle und kann auf verschiedenen Plattformen arbeiten
JavaScript-Interpreter: Wird zum Parsen und Ausführen von JavaScript-Code verwendet
Benutzeroberfläche Backend: Wird zum Zeichnen grundlegender Widgets wie Kombinationsfelder und Fenster verwendet.
Datenspeicher: Er gehört zur Persistenzschicht. Der Browser speichert verschiedene Daten wie Cookies auf der Festplatte Festplatte, HTML5 Definiert die Webdatenbanktechnologie, eine leichte und vollständige clientseitige Speichertechnologie. Jede Registerkarte ist ein unabhängiger Prozess
3 Sagen Sie mir, was von der Eingabe der URL bis zum Rendern der Seite passiert. Man kann sagen, dass diese Frage die häufigste Frage in Vorstellungsgesprächen ist und unendlich schwierig sein kann. Im Allgemeinen stellen Interviewer diese Frage, um die Tiefe Ihres Front-End-Wissens zu testen.
1. Der Browser akzeptiert die URL und öffnet den Netzwerkanforderungsthread (einschließlich: Browsermechanismus, Thread und Prozess usw.)
3. Empfangen Sie die Anfrage vom Server an das entsprechende Backend, um die Anfrage zu empfangen (einschließlich: Lastausgleich, Sicherheitsabfangen, interne Backend-Verarbeitung usw.) 4 . HTTP-Interaktion zwischen dem Backend und dem Frontend (einschließlich: http-Header, Antwortcodes, Nachrichtenstrukturen, Cookies usw.)
5. Cache-Probleme (einschließlich: http-starker Cache und ausgehandelter Cache, Cache-Header, Etag, abgelaufen, Cache-Steuerung usw.)
6. Browser Der Analyseprozess nach dem Empfang des http-Datenpakets (einschließlich lexikalischer HTML-Analyse, Analyse in einen DOM-Baum, Analyse von CSS zum Generieren eines CSSOM-Baums und Zusammenführen zum Generieren eines Renderbaums. Dann Layout, Mal-Rendering, zusammengesetzte Ebenensynthese, GPU-Zeichnung, Verarbeitung externer Links usw.)
7. Visuelles CSS-Modell (einschließlich: Element-Rendering-Regeln, wie z. B. enthaltender Block, Steuerfeld, BFC, IFC usw.)
8. JS-Engine-Analyseprozess (einschließlich: JS-Analysephase, Vorverarbeitungsphase, die Ausführungsphase generiert Ausführungskontext, VO (globales Objekt), Bereichskette, Recyclingmechanismus usw.)
Sie werden feststellen, dass es so viele gibt Haben Sie das Gefühl, dass die Prozesse zwischen einer einfachen Eingabe-URL und dem Rendern der Seite sofort abstürzen? (Keine Sorge, wir werden in diesem Kapitel nicht näher darauf eingehen. Wir zeigen Ihnen zunächst, wie Sie diese Frage beantworten können.) . Dieser Abschnitt wird später in einem separaten Artikel behandelt) Der Browser erhält die IP-Adresse des Domänennamens über den DNS-Server und sendet eine Anfrage an diese IP-Adresse, um den HTML-Text abzurufenDer Browser-Rendering-Prozess analysiert den HTML-Text und erstellt den DOM-BaumWenn beim Parsen des HTML ein Inline-Stil oder eine Stildatei gefunden wird, werden die Stilregeln heruntergeladen und erstellt. Wenn es auf ein JavaScript-Skript stößt, wird es heruntergeladen
Nachdem der DOM-Baum und CSSOM erstellt wurden, führt der Renderprozess die beiden zu einem Renderbaum zusammen.HTML in viele Token analysierenToken in Objekte analysieren
Objekte in einem DOM-Baum kombinierenDas wissen wir Der DOM-Baum und der CSSOM-Baum werden im Renderbaum zusammengeführt, der das CSSOM tatsächlich an den DOM-Baum anhängt. Daher muss der DOM-Baum basierend auf den vom Selektor bereitgestellten Informationen durchlaufen werden. Sehen wir uns ein Beispiel an:
<style> .nav .title span {color:blue} </style> <div class='nav'> <div class='title'> <span>南玖</span> </div> <div class="sub_title">前端</header> </div>
Rechts-nach-links-Übereinstimmung:
Suchen Sie zunächst alle Knotenbereiche ganz rechts und suchen Sie für jeden Bereich aufwärts nach dem Knoten div.title
von h3 und dann nach oben Wenn der Knoten von div.nav
schließlich das Stammelement HTML findet, endet die Durchquerung dieses Zweigs.
Wenn der Browser auf JS-Code stößt, ruft er sofort den „JS-Parser“ auf, um zu arbeiten. Der Parser findet alle Variablen, Funktionen, Parameter usw. in js und weist den Variablenwert undefiniert zu. Nehmen Sie die Funktion in einen Funktionsblock und speichern Sie ihn im Warehouse. Danach wird der Code Zeile für Zeile analysiert (von oben nach unten, von links nach rechts) und dann mit dem Warehouse abgeglichen. Neuzeichnen führt nicht unbedingt zu Neufließen, aber Neuzeichnen führt definitiv zu Neuzeichnen Anleitung Neuzeichnen und Umfließen auslösen? Jede Änderung der zum Erstellen des Renderbaums verwendeten Informationen führt zu einem Reflow oder Neuzeichnen: Wie vermeide ich ein Neuzeichnen oder Umfließen? Konzentrierte Stiländerung: Verwenden Sie beispielsweise die Klasse, um Stile kollektiv zu ändern. Verwenden Sie 提升为合成层 将元素提升为合成层有以下优点: 合成层的位图,会交由 当需要 对于 提升合成层的最好方式是使用 CSS 的 这主要与JS的用途有关,JS作为浏览器的脚本语言,最初主要是实现用户与浏览器的交互,以及操作DOM。这就决定了它只能是单线程,否则会带来许多复杂的同步问题。 举个例子: 如果JS是多线程的,其中一个线程要修改一个DOM元素,另外一个线程想要删除这个DOM元素,这时候浏览器就不知道该听谁的。所以为了避免复杂性,从一诞生,JavaScript就被设计成单线程。 为了利用多核CPU的计算能力,HTML5提出Web Worker标准,允许JavaScript脚本创建多个线程,但是子线程完全受主线程控制,且不得操作DOM。所以,这个新标准并没有改变JavaScript单线程的本质 先上结论 CSSOM的作用 第一个是提供给JavaScript操作样式表的能力 第二个是为布局树的合成提供基础的样式信息 这个CSSOM体现在DOM中就是 Dies hängt hauptsächlich mit dem Zweck von JS zusammen. Als Skriptsprache des Browsers wurde JS zunächst hauptsächlich dazu verwendet, die Interaktion zwischen dem Benutzer und dem Browser zu realisieren und das DOM zu bedienen. Dies legt fest, dass es nur Single-Threaded sein kann, da es sonst viele komplexe Synchronisationsprobleme mit sich bringt. Um die Rechenleistung von Multi-Core-CPUs zu nutzen, schlägt HTML5 den Web Worker-Standard vor, der es JavaScript-Skripten ermöglicht, mehrere Threads zu erstellen, die untergeordneten Threads werden jedoch vollständig vom Haupt-Thread gesteuert und dürfen den nicht bedienen DOM. Daher ändert dieser neue Standard nichts an der Single-Threaded-Natur von JavaScript. Wenn der Inhalt des 避免白屏,提高CSS的加载速度 先上结论 JS会阻塞DOM的解析,因此也就会阻塞页面的加载 这也是为什么我们常说要把JS文件放在最下面的原因 由于 JavaScript 是可操纵 DOM 的,如果在修改这些元素属性同时渲染界面(即 JavaScript 线程和 UI 线程同时运行),那么渲染线程前后获得的元素数据就可能不一致了。 因此为了防止渲染出现不可预期的结果,浏览器设置 **「GUI 渲染线程与 JavaScript 引擎为互斥」**的关系。 当 JavaScript 引擎执行时 GUI 线程会被挂起,GUI 更新会被保存在一个队列中等到引擎线程空闲时立即被执行。 当浏览器在执行 JavaScript 程序的时候,GUI 渲染线程会被保存在一个队列中,直到 JS 程序执行完成,才会接着执行。 因此如果 JS 执行的时间过长,这样就会造成页面的渲染不连贯,导致页面渲染加载阻塞的感觉。 Reduzieren Sie die Anzahl der HTTP-Anfragen und führen Sie CSS-Dateien zusammen. Lassen Sie uns zuerst zum Schluss kommen und daher das Laden der Seite Aus diesem Grund sagen wir oft, dass wir die JS-Datei unten platzieren sollten Da JavaScript das DOM manipulieren kann, werden die Elementdaten vor und nach dem Rendering-Thread abgerufen, wenn Sie die Eigenschaften dieser Elemente während des Renderns der Schnittstelle ändern (dh der JavaScript-Thread und der UI-Thread werden gleichzeitig ausgeführt). kann inkonsistent sein. Wenn die JavaScript-Engine ausgeführt wird, wird der GUI-Thread angehalten und GUI-Updates werden in einer Warteschlange gespeichert und sofort ausgeführt, wenn der Engine-Thread inaktiv ist. Wenn also die Ausführungszeit von JS zu lang ist, führt dies dazu, dass das Rendern der Seite inkohärent ist, was zu dem Gefühl führt, dass das Rendern und Laden der Seite blockiert ist. 5.Was ist der Unterschied zwischen DOMContentLoaded und Load?
6. Was ist der Unterschied zwischen Browser-Neuzeichnung und Domain-Neuanordnung?
document.createDocumentFragment()
: Wir können ein Dokument erstellen, das frei vom DOM-Baum ist Über den Knoten „createDocumentFragment“ werden dann Stapeloperationen auf diesem Knoten ausgeführt und schließlich in den DOM-Baum eingefügt, sodass nur ein Reflow ausgelöst wird. document.createDocumentFragment()
:我们可以通过createDocumentFragment创建一个游离于DOM树之外的节点,然后在此节点上批量操作,最后插入DOM树中,因此只触发一次重排GPU
合成,比 CPU
处理要快repaint
时,只需要 repaint
本身,不会影响到其他的层transform
和 opacity
效果,不会触发 layout
和 paint
will-change
属性7.为什么JS是单线程的?
8.CSS加载会阻塞DOM吗?
CSS
不会阻塞DOM
的解析,但会阻塞DOM
的渲染CSS
会阻塞JS
执行,但不会阻塞JS
文件的下载
Die Teile der Kompositionsebene Das Bild wird von der document.styleSheets
GPU
synthetisiert, was schneller ist als die CPU
-Verarbeitungrepaint</code > ist erforderlich, nur <code>repaint< /code> selbst hat keinen Einfluss auf andere Ebenen<p><strong></strong></p>Für die Effekte <code>transform
und opacity
, layout</ code> und <code wird nicht ausgelöst >paint
will-change
7. Warum ist JS Single-Threaded?
8 Wird das Laden von CSS das DOM blockieren?
🎜🎜
🎜🎜🎜Die Rolle von CSSOM🎜 🎜🎜🎜🎜🎜Die erste besteht darin, JavaScript die Möglichkeit zu geben, Stylesheets zu bedienen. 🎜🎜🎜🎜 Die zweite besteht darin, grundlegende Stilinformationen für die Synthese von Layoutbäumen bereitzustellen. 🎜🎜🎜🎜Dieses CSSOM wird im DOM als CSS
blockiert nicht das Parsen von DOM
, aber es blockiert das Rendern von DOM< /code> 🎜🎜<code>CSS
blockiert die Ausführung von JS
, aber nicht den Download von JS
-Dateien🎜🎜document .styleSheets
widergespiegelt 🎜🎜🎜🎜Wir können anhand des zuvor erwähnten Browser-Rendering-Prozesses erkennen: 🎜🎜🎜🎜DOM und CSSOM werden normalerweise parallel erstellt, sodass 🎜CSS nicht geladen wird DOM-Parsing blockieren🎜🎜🎜 🎜🎜Der Renderbaum hängt vom DOM-Baum und dem CSSOM-Baum ab, daher muss er warten, bis beide geladen sind, bevor er mit dem Erstellen des Renderings beginnen kann, sodass 🎜CSS-Laden das Rendern des DOM blockiert🎜🎜🎜🎜 🎜Da JavaScript DOM und CSS bedienen kann, können beim Rendern der Schnittstelle die Eigenschaften dieser Elemente geändert werden (d. h. der JavaScript-Thread und der UI-Thread werden gleichzeitig ausgeführt), die Elemente können vor und nach dem Rendering-Thread abgerufen werden inkonsistent sein. Um unerwartete Rendering-Ergebnisse zu verhindern, stellt der Browser den 🎜GUI-Rendering-Thread und den JavaScript-Thread so ein, dass sie sich gegenseitig ausschließen. JS muss auf den Download von CSS warten. (CSS blockiert die DOM-Ausführung)🎜🎜🎜JS
-Skripts darin besteht, den Stil des Elements zu erhalten, muss es auf CSS
zurückgreifen. Da der Browser nicht erkennen kann, was in JS
vor sich geht, muss er warten, bis alle vorherigen Stile heruntergeladen wurden, bevor er JS
ausführt, um eine Stilübernahme zu vermeiden. Allerdings werden JS-Dateien und CSS-Dateien parallel heruntergeladen. Die CSS-Datei wird geladen und ausgeführt, bevor die nachfolgende JS-Datei ausgeführt wird, sodass JS
脚本的内容是获取元素的样式,那它就必然依赖CSS
。因为浏览器无法感知JS
内部到底想干什么,为避免样式获取,就只好等前面所有的样式下载完毕再执行JS
。但JS文件与CSS文件下载是并行的,CSS文件会在后面的JS文件执行前先加载执行完毕,所以CSS会阻塞后面JS的执行9.JS会阻塞页面吗?
10.defer和async的区别?
DOMContentLoaded
事件前执行,如果缺少 src
CSS die Ausführung nachfolgender JS blockiertVermeiden Sie den weißen Bildschirm und verbessern Sie die Ladegeschwindigkeit von CSS
Verwenden Sie CDN (CDN wählt den nächstgelegenen Knoten mit zwischengespeichertem Inhalt aus, um Ihnen Ressourcen basierend auf Ihren Netzwerkbedingungen bereitzustellen, sodass die Ladezeit verkürzt werden kann) Komprimieren Sie CSS Verwenden Sie den Cache sinnvoll 9 Wird JS die Seite blockieren?
Wenn der Browser ein JavaScript-Programm ausführt, wird der GUI-Rendering-Thread in einer Warteschlange gespeichert und erst ausgeführt, wenn das JS-Programm abgeschlossen ist. 10. Was ist der Unterschied zwischen aufschieben und asynchron?
DOMContentLoaded
ausgelöst wird, wenn das Attribut src
(d. h. eingebettetes Skript) vorhanden ist. fehlt, sollte dieses Attribut nicht verwendet werden, da es in diesem Fall nicht funktioniert Die Garbage-Collection ist ein automatischer Speicherverwaltungsmechanismus. Dynamischer Speicher auf Ihrem Computer sollte freigegeben werden, wenn er nicht mehr benötigt wird.
Es ist zu beachten, dass automatisch bedeutet, dass der Browser uns automatisch dabei helfen kann, Speichermüll zu recyceln. Dies bedeutet jedoch nicht, dass wir uns nicht um die Speicherverwaltung kümmern müssen. Wenn es nicht ordnungsgemäß ausgeführt wird, kommt es in JavaScript immer noch zu einem Speicherüberlauf , was zum Absturz des Systems führt. 🎜🎜🎜Da Strings, Arrays, Objekte usw. keine feste Größe haben, müssen sie dynamisch zugewiesen werden, wenn ihre Größe bekannt ist. Jedes Mal, wenn ein JavaScript-Programm eine Zeichenfolge, ein Array oder ein Objekt erstellt, muss der Interpreter Speicher zum Speichern dieser Entität zuweisen. 🎜🎜Der JavaScript-Interpreter kann erkennen, wenn das Programm ein Objekt nicht mehr verwendet. Wenn es feststellt, dass das Objekt nutzlos ist, weiß es, dass das Objekt nicht mehr benötigt wird, und kann den von ihm belegten Speicher freigeben. 🎜🎜Es gibt zwei Methoden der Garbage Collection, die normalerweise von Browsern verwendet werden: 🎜Mark Sweep🎜, 🎜Reference Counting🎜. 🎜🎜🎜🎜Mark Clearing🎜🎜🎜🎜🎜Dies ist die am häufigsten verwendete Garbage-Collection-Methode in JavaScript🎜🎜🎜Seit 2012 verwenden alle modernen Browser die Mark-Clearing-Garbage-Collection-Methode, mit Ausnahme niedrigerer Versionen des IE. Referenzzählung. 🎜🎜🎜Was ist also die Entfernung von Markierungen? 🎜🎜🎜🎜Es gibt ein globales Objekt in JavaScript. Der Garbage Collector beginnt regelmäßig mit diesem globalen Objekt, sucht alle Objekte, auf die von diesem globalen Objekt verwiesen wird, und findet dann die Objekte, auf die diese Objekte verweisen ... Für diese aktiven Objekte Markierung, dies ist die Markierungsphase. In der Löschphase werden die nicht markierten Objekte gelöscht. 🎜🎜🎜Ein Problem beim Löschen von Markierungen besteht darin, dass der Speicherplatz nach dem Löschen diskontinuierlich ist, d. h. es kommt zu einer Speicherfragmentierung. Wenn später ein relativ großer kontinuierlicher Speicherplatz benötigt wird, wird dieser den Anforderungen nicht gerecht. Die Methode der „Markenorganisation“ kann dieses Problem effektiv lösen. 🎜🎜Beim Markieren wird das Konzept der dreifarbigen Markierung eingeführt. Die drei Farben sind: 🎜🎜🎜Weiß: Nicht markierte Objekte, also nicht erreichbare Objekte (Objekte, die nicht gescannt werden), können recycelt werden. 🎜🎜Grau : Objekte, die markiert wurden (erreichbare Objekte), aber die Objekte wurden noch nicht gescannt und können nicht recycelt werden 🎜🎜Schwarz: wurden gescannt (erreichbare Objekte) und können nicht recycelt werden 🎜🎜🎜🎜 Markierungssortierung: 🎜🎜Die Markierungsphase unterscheidet sich nicht von der Markierungs- und Löschmethode, außer dass die Markierungs- und Löschmethode nach Abschluss der Markierung die verbleibenden Objekte auf eine Seite des Speichers verschiebt und schließlich den Grenzspeicher bereinigt.
Referenzzählung
Die Bedeutung der Referenzzählung besteht darin, zu verfolgen, wie oft auf jeden Wert verwiesen wird. Wenn einer Variablen A ein Wert zugewiesen wird, beträgt die Anzahl der Verweise auf diesen Wert 1. Wenn Variable A neu zugewiesen wird, verringert sich die Anzahl der Verweise auf den vorherigen Wert um 1. Wenn die Anzahl der Referenzen 0 wird, bedeutet dies, dass es keine Möglichkeit mehr gibt, auf diesen Wert zuzugreifen, sodass der von diesem Wert belegte Speicher gelöscht werden kann.
Die meisten Browser haben diese Recyclingmethode aufgegeben
Speicherleck
Um Speicherlecks zu vermeiden, ist es am besten, den Wert auf
null</ zu setzen, sobald die Daten nicht mehr verwendet werden. Code>Um seine Referenz freizugeben, heißt diese Methode <code>null
来释放其引用,这个方法叫做接触引用
哪些情况会造成内存泄漏?如何避免?
以 Vue 为例,通常有这些情况:
window/body
等事件没有解绑EventBus
的事件没有解绑Vuex
的 $store
,watch
了之后没有 unwatch
解决办法:beforeDestroy
中及时销毁
DOM/BOM
对象中的事件 addEventListener
,removeEventListener
。$on
,$off
处理。mounted/created
钩子中使用了第三方库初始化,对应的销毁。weakMap
、weakSet
。浏览器中不同类型变量的内存都是何时释放的?
引用类型
基本类型
认识浏览器缓存
当浏览器请求一个网站时,会加载各种资源,对于一些不经常变动的资源,浏览器会将他们保存在本地内存中,下次访问时直接加载这些资源,提高访问速度。
如何知道资源是请求的服务器还是读取的缓存呢?
看上面这张图,有些资源的size值是大小,有些是from disk cache
,有些是from memory cache
,显示大小的是请求的服务器资源,而显示后面两种的则是读取的缓存。
CurlCacheManager
KontaktreferenzEreignisse, die in window/body überwacht werden, sind nicht ungebunden | Ereignisse, die an EventBus gebunden sind, sind nicht entbunden Nach dem Entbinden von | Vuex s $store wird watch nicht mit unwatch |
---|---|---|
Beobachtermodus | Wenn in einer Komponente ein Timer verwendet wird, sollte dieser zerstört werden. | |
Verwenden Sie schwache Referenzen | Wann werden die Speicher verschiedener Variablentypen im Browser freigegeben? | |
Referenztypen |
aus dem Festplatten-Cache
und andere sind aus dem Speicher-Cache
Die beiden letztgenannten werden als Lesecache angezeigt. 🎜CurlCacheManager
. (Die Effizienz ist langsamer als beim Speichercache, aber die Speicherkapazität ist groß und die Speicherzeit ist lang) 🎜🎜🎜Speichercache: 🎜 Es dient dazu, Ressourcen im Speicher zwischenzuspeichern und auf den nächsten Zugriff zu warten, ohne sie erneut herunterzuladen. direkt aus dem Gedächtnis lesen. (Aus Sicht der Effizienz ist es am schnellsten und aus Sicht der Überlebenszeit am kürzesten.) Speichern Sie nur einige abgeleitete Ressourcendateien.🎜🎜Nur einige abgeleitete Ressourcendateien können gespeichert werden.🎜🎜🎜🎜Der Unterschied Ressourcen🎜🎜Allgemeine Skripte, Schriftarten und Bilder werden im Speicher gespeichert. Im Allgemeinen werden Nicht-Skripte wie CSS usw. im Speicher gespeichert.🎜🎜🎜🎜Browser-Cache-Klassifizierung
Wenn der Browser Ressourcen vom Server anfordert, ermittelt er zunächst, ob er auf den starken Cache trifft, und wenn dies fehlschlägt, bestimmt er, ob er trifft der Verhandlungscache
Starker Cache
Wenn der Browser Ressourcen lädt, ermittelt er zunächst anhand des Headers
der lokalen Cache-Ressource, ob er trifft , wird die Ressource im Cache direkt verwendet und nicht erneut an den Cache gesendet. Der Server sendet die Anfrage. header
中判断是否命中强缓存,如果命中则直接使用缓存中的资源,不会再向服务器发送请求。 (这里的header中的信息指的是 expires
和 cache-control
)
Expires
该字段是 http1.0 时的规范,它的值为一个绝对时间的 GMT 格式的时间字符串,比如 Expires:Mon,18 Oct 2066 23:59:59 GMT。这个时间代表着这个资源的失效时间,在此时间之前,即命中缓存。这种方式有一个明显的缺点,由于失效时间是一个绝对时间,所以当服务器与客户端时间偏差较大时,就会导致缓存混乱。所以这种方式很快在后来的HTTP1.1版本中被抛弃了。
Cache-Control
Cache-Control 是 http1.1 时出现的 header 信息,主要是利用该字段的 max-age 值来进行判断,它是一个相对时间,例如 Cache-Control:max-age=3600
,代表着资源的有效期是 3600 秒。cache-control 除了该字段外,还有下面几个比较常用的设置值:
no-cache:需要进行协商缓存,发送请求到服务器确认是否使用缓存。
no-store:禁止使用缓存,每一次都要重新请求数据。
public:可以被所有的用户缓存,包括终端用户和 CDN 等中间代理服务器。
private:只能被终端用户的浏览器缓存,不允许 CDN 等中继缓存服务器对其缓存。
Cache-Control 与 Expires 可以在服务端配置同时启用,同时启用的时候 Cache-Control 优先级高。
协商缓存
当强缓存没命中时,浏览器会发送一个请求到服务器,服务器根据 header
中的信息来判断是否命中协商缓存。如果命中,则返回304 ,告诉浏览器资源未更新,可以使用本地缓存。 (这里的header信息指的是Last-Modify/If-Modify-Since
和 ETag/If-None-Match
(Die Informationen in der Kopfzeile hier beziehen sich auf expires
und cache-control
)
Expires
Dieses Feld ist
http1.0Bei der Zeitangabe handelt es sich bei dem Wert um eine
absolute ZeitZeitzeichenfolge im GMT-Format, z. B. Läuft ab:Mo,18. Okt. 2066 23:59:59 GMT. Diese Zeit stellt die Ablaufzeit dieser Ressource dar. Vor diesem Zeitpunkt wird der Cache erreicht. Diese Methode weist einen offensichtlichen Nachteil auf. Da es sich bei der Ablaufzeit um eine absolute Zeit handelt, führt eine große Zeitabweichung zwischen dem Server und dem Client zu Cache-Verwirrung. Daher wurde diese Methode in der späteren Version von HTTP 1.1 schnell aufgegeben.
Cache-ControlCache-Control ist die Header-Information, die bei http1.1 angezeigt wird. Sie wird hauptsächlich anhand des
max-ageCache-Control:max-age=3600
, dass die Ressourcengültigkeitsdauer 3600 Sekunden beträgt. Zusätzlich zu diesem Feld verfügt die Cache-Steuerung auch über die folgenden häufiger verwendeten Einstellungswerte: no-cache
: Sie müssen den Cache aushandeln und eine Anfrage an den Server senden, um zu bestätigen, ob der Cache verwendet werden soll.no-store
: Caching deaktivieren und Daten jedes Mal neu anfordern.öffentlich: Kann von allen Benutzern zwischengespeichert werden, einschließlich Endbenutzern und zwischengeschalteten Proxyservern wie CDN.
privat: Es kann nur vom Browser des Endbenutzers zwischengespeichert werden und darf nicht von Relay-Cache-Servern wie CDN zwischengespeichert werden.
Cache-Control und Expires können gleichzeitig in der Serverkonfiguration aktiviert werden. Bei gleichzeitiger Aktivierung hat Cache-Control eine höhere Priorität.
Negotiation Cache🎜🎜Wenn der starke Cache fehlschlägt, sendet der Browser eine Anfrage an den Server und der Server bestimmt anhand der Informationen imheader
, ob der Aushandlungcache erreicht wird . Bei einem Treffer wird 🎜304🎜 zurückgegeben und teilt dem Browser mit, dass die Ressource nicht aktualisiert wurde und der lokale Cache verwendet werden kann. 🎜(Die Header-Informationen hier beziehen sich auf Last-Modify/If-Modify-Since
und ETag/If-None-Match
)🎜🎜🎜🎜🎜🎜Last-Modify / If-Modify-Since🎜🎜🎜🎜🎜Wenn der Browser zum ersten Mal eine Ressource anfordert, wird „Last-Modify“ zum vom Server zurückgegebenen Header hinzugefügt. „Last-Modify“ ist eine Zeitangabe, die den Zeitpunkt der letzten Änderung der Ressource angibt . 🎜🎜Wenn der Browser die Ressource erneut anfordert, enthält der Anforderungsheader „If-Modify-Since“, also die letzte Änderung, die vor dem Caching zurückgegeben wird. Nachdem der Server If-Modify-Since empfangen hat, bestimmt er anhand der letzten Änderungszeit der Ressource, ob der Cache erreicht wird. 🎜🎜Wenn der Cache erreicht wird, wird 304 zurückgegeben und der Ressourceninhalt wird nicht zurückgegeben und Last-Modify wird nicht zurückgegeben. 🎜🎜Nachteile:🎜🎜Wenn sich die Ressourcen in kurzer Zeit ändern, ändert sich Last-Modified nicht. 🎜🎜Zyklische Veränderungen. Wenn diese Ressource innerhalb eines Zyklus wieder in ihr ursprüngliches Aussehen zurückversetzt wird, gehen wir davon aus, dass sie zwischengespeichert werden kann, Last-Modified glaubt dies jedoch nicht, daher gibt es ein ETag. 🎜🎜🎜🎜🎜ETag/If-None-Match🎜🎜🎜🎜🎜Der Unterschied zu Last-Modify/If-Modify-Since besteht darin, dass Etag/If-None-Match einen Prüfcode zurückgibt. ETag kann garantieren, dass jede Ressource einzigartig ist und Ressourcenänderungen zu ETag-Änderungen führen. Der Server bestimmt anhand des vom Browser gesendeten If-None-Match-Werts, ob der Cache erreicht wird. 🎜🎜Der Unterschied zu Last-Modified besteht darin, dass, wenn der Server eine 304 Not Modified-Antwort zurückgibt, das ETag im Antwortheader zurückgegeben wird, da das ETag neu generiert wurde, auch wenn sich das ETag gegenüber dem vorherigen nicht geändert hat. 🎜🎜🎜Last-Modified und ETag können zusammen verwendet werden. Der Server überprüft zunächst das ETag, vergleicht es dann weiter und entscheidet schließlich, ob 304 zurückgegeben wird. 🎜🎜🎜🎜🎜Zusammenfassung🎜🎜🎜🎜🎜Wenn der Browser auf eine bereits besuchte Ressource zugreift, sind seine Schritte: 🎜🎜🎜1. Überprüfen Sie zunächst, ob der starke Cache getroffen wird?, Verwenden Sie den Cache direkt . Wenn der starke Cache nicht erreicht wird, wird die Anfrage an den Server gesendet, um zu sehen, ob er den Verhandlungscache erreicht. 🎜🎜3 Wenn der Verhandlungscache erreicht wird, gibt der Server 304 zurück, um dem Browser mitzuteilen, dass der lokale Cache vorhanden ist 4. Wenn der Verhandlungscache nicht erreicht wird, gibt der Server neue Ressourcen an den Browser zurück🎜同源策略
同源策略是浏览器的一种自我保护行为。所谓的同源指的是:协议,域名,端口均要相同
浏览器中大部分内容都是受同源策略限制的,但是以下三个标签不受限制:
<img src="..." / alt="Schauen Sie sich diese Browser-Interviewfragen an. Wie viele können Sie richtig beantworten?" > <link href="..." /> <script src="..."></script>
跨域
跨域指的是浏览器不能执行其它域名下的脚本。它是由浏览器的同源策略限制的。
你可能会想跨域请求到底有没有发送到服务器?
事实上,跨域请求时能够发送到服务器的,并且服务器也能过接受的请求并正常返回结果,只是结果被浏览器拦截了。
JSONP
它主要是利用script标签不受浏览器同源策略的限制,可以拿到从其他源传输过来的数据,需要服务端支持。
优缺点:
兼容性比较好,可用于解决主流浏览器的跨域数据访问的问题。缺点就是仅支持get请求,具有局限性,不安全,可能会受到XSS攻击。
思路:
<script>
标签,把那个跨域的API数据接口地址,赋值给script的src,还要在这个地址中向服务器传递该函数名(可以通过问号传参:?callback=show)。show('南玖')
。// front function jsonp({ url, params, callback }) { return new Promise((resolve, reject) => { let script = document.createElement('script') window[callback] = function(data) { resolve(data) document.body.removeChild(script) } params = { ...params, callback } // wd=b&callback=show let arrs = [] for (let key in params) { arrs.push(`${key}=${params[key]}`) } script.src = `${url}?${arrs.join('&')}` document.body.appendChild(script) }) } jsonp({ url: 'http://localhost:3000/say', params: { wd: 'wxgongzhonghao' }, callback: 'show' }).then(data => { console.log(data) })
// server 借助express框架 let express = require('express') let app = express() app.get('/say', function(req, res) { let { wd, callback } = req.query console.log(wd) // Iloveyou console.log(callback) // show res.end(`${callback}('关注前端南玖')`) }) app.listen(3000)
上面这段代码相当于向http://localhost:3000/say?wd=wxgongzhonghao&callback=show
这个地址请求数据,然后后台返回show('关注前端南玖')
,最后会运行show()这个函数,打印出'关注前端南玖'
跨域资源共享(CORS)
CORS(Cross-Origin Resource Sharing)跨域资源共享,定义了必须在访问跨域资源时,浏览器与服务器应该如何沟通。CORS背后的基本思想是使用自定义的HTTP头部让浏览器与服务器进行沟通,从而决定请求或响应是应该成功还是失败。
CORS 需要浏览器和后端同时支持。IE 8 和 9 需要通过 XDomainRequest 来实现。
浏览器会自动进行 CORS 通信,实现 CORS 通信的关键是后端。只要后端实现了 CORS,就实现了跨域。
服务端设置 Access-Control-Allow-Origin 就可以开启 CORS。 该属性表示哪些域名可以访问资源,如果设置通配符则表示所有网站都可以访问资源。
虽然设置 CORS 和前端没什么关系,但是通过这种方式解决跨域问题的话,会在发送请求时出现两种情况,分别为简单请求和复杂请求。
简单请求: (满足以下两个条件,就是简单请求)
1.请求方法为以下三个之一:
2.Content-Type的为以下三个之一:
复杂请求:
不是简单请求那它肯定就是复杂请求了。复杂请求的CORS请求,会在正式发起请求前,增加一次HTTP查询请求,称为预检 请求,该请求是option方法的,通过该请求来知道服务端是否允许该跨域请求。
Nginx 反向代理的原理很简单,即所有客户端的请求都必须经过nginx处理,nginx作为代理服务器再将请求转发给后端,这样就规避了浏览器的同源策略。
什么是XSS?
XSS 全称是
Cross Site Scripting
,为了与css
区分开来,所以简称XSS
,中文叫作跨站脚本XSS是指黑客往页面中注入恶意脚本,从而在用户浏览页面时利用恶意脚本对用户实施攻击的一种手段。
XSS能够做什么?
XSS实现方式
如何阻止XSS攻击?
对输入脚本进行过滤或转码
对用户输入的信息过滤或者转码,保证用户输入的内容不能在HTML解析的时候执行。
利用CSP
该安全策略的实现基于一个称作
Content-Security-Policy
的HTTP首部。(浏览器内容安全策略)它的核心思想就是服务器决定浏览器加载那些资源。
利用 HttpOnly
由于很多 XSS 攻击都是来盗用 Cookie 的,因此还可以通过使用 HttpOnly 属性来保护我们 Cookie 的安全。这样子的话,JavaScript 便无法读取 Cookie 的值。这样也能很好的防范 XSS 攻击。
通常服务器可以将某些 Cookie 设置为 HttpOnly 标志,HttpOnly 是服务器通过 HTTP 响应头来设置的,下面是打开 Google 时,HTTP 响应头中的一段:
set-cookie: NID=189=M8l6-z41asXtm2uEwcOC5oh9djkffOMhWqQrlnCtOI; expires=Sat, 18-Apr-2020 06:52:22 GMT; path=/; domain=.google.com; HttpOnly
对于不受信任的输入,可以限制输入长度
什么是CSRF攻击?
CSRF 全称
Cross-site request forgery
,中文为跨站请求伪造 ,攻击者诱导受害者进入第三方网站,在第三方网站中,向被攻击网站发送跨站请求。利用受害者在被攻击网站已经获取的注册凭证,绕过后台的用户验证,达到冒充用户对被攻击的网站执行某项操作的目的。 CSRF攻击就是黑客利用用户的登录状态,并通过第三方站点来干一些嘿嘿嘿的坏事。
几种常见的攻击类型
1.GET类型的CSRF
GET类型的CSRF非常简单,通常只需要一个HTTP请求:
<img src="http://bank.example/withdraw?amount=10000&for=hacker" alt="Schauen Sie sich diese Browser-Interviewfragen an. Wie viele können Sie richtig beantworten?" >
在受害者访问含有这个img的页面后,浏览器会自动向http://bank.example/withdraw?account=xiaoming&amount=10000&for=hacker
发出一次HTTP请求。bank.example就会收到包含受害者登录信息的一次跨域请求。
2.POST类型的CSRF
这种类型的CSRF利用起来通常使用的是一个自动提交的表单,如:
<form action="http://bank.example/withdraw" method=POST> <input type="hidden" name="account" value="xiaoming" /> <input type="hidden" name="amount" value="10000" /> <input type="hidden" name="for" value="hacker" /> </form> <script> document.forms[0].submit(); </script>
访问该页面后,表单会自动提交,相当于模拟用户完成了一次POST操作。
3.链接类型的CSRF
链接类型的CSRF并不常见,比起其他两种用户打开页面就中招的情况,这种需要用户点击链接才会触发。这种类型通常是在论坛中发布的图片中嵌入恶意链接,或者以广告的形式诱导用户中招,攻击者通常会以比较夸张的词语诱骗用户点击,例如:
<a href="http://test.com/csrf/withdraw.php?amount=1000&for=hacker" taget="_blank"> 重磅消息!! <a/>
由于之前用户登录了信任的网站A,并且保存登录状态,只要用户主动访问上面的这个PHP页面,则表示攻击成功。
CSRF的特点
CSRF通常是跨域的,因为外域通常更容易被攻击者掌控。但是如果本域下有容易被利用的功能,比如可以发图和链接的论坛和评论区,攻击可以直接在本域下进行,而且这种攻击更加危险。
防护策略
Ein Hacker kann das Cookie
des Opfers nur verwenden, um das Vertrauen des Servers zu missbrauchen, aber der Hacker kann das **„Cookie“** nicht erhalten und den Inhalt des **„Cookies“ nicht sehencookie
骗取服务器的信任,但是黑客并不能凭借拿到**「cookie」**,也看不到 **「cookie」的内容。另外,对于服务器返回的结果,由于浏览器「同源策略」**的限制,黑客也无法进行解析。
这就告诉我们,我们要保护的对象是那些可以直接产生数据改变的服务,而对于读取数据的服务,则不需要进行
„Fügen Sie Informationen in die Anfrage ein, die Hacker nicht fälschen können“CSRF
. Darüber hinaus können Hacker die vom Server zurückgegebenen Ergebnisse aufgrund der Einschränkungen der „Same Origin Policy“** des Browsers nicht analysieren. Dies sagt uns, dass es sich bei den Objekten, die wir schützen möchten, um Dienste handelt, die direkt Datenänderungen hervorrufen können, und dass für Dienste, die Daten lesen, keinCSRF
-Schutz erforderlich ist. Der Schlüssel zum Schutz ist
Originalerkennung
Da die meisten CSRFs von Websites Dritter stammen, verbieten wir direkt externe Domänen (oder nicht vertrauenswürdige Domänen). Namen) Anfragen an uns richten.
Dann stellt sich die Frage: Wie stellen wir fest, ob die Anfrage von einer externen Domain kommt?
Wenn der Browser eine Anfrage initiiert, werden diese beiden Header in den meisten Fällen verwendet automatisch gebracht und der Inhalt kann nicht vom Frontend angepasst werden. Der Server kann die Quelldomäne der Anforderung ermitteln, indem er die Domänennamen in diesen beiden Headern analysiert.
Verwenden Sie den Origin-Header, um den Quelldomänennamen zu bestimmen.Bei einigen CSRF-bezogenen Anfragen wird das Origin-Feld im angeforderten Header enthalten. Das Feld enthält den angeforderten Domänennamen (ohne Pfad und Abfrage).
Wenn Origin vorhanden ist, können Sie die Felder in Origin direkt verwenden, um den Quelldomänennamen zu bestätigen.
Verwenden Sie den Referrer-Header, um den Quelldomänennamen zu ermitteln.
Gemäß dem HTTP-Protokoll gibt es im HTTP-Header ein Feld namens Referer, das die Quelladresse der HTTP-Anfrage aufzeichnet. Bei Ajax-Anfragen, Ressourcenanfragen wie Bildern und Skripten ist der Referrer die Seitenadresse, die die Anfrage initiiert. Bei Seitensprüngen ist Referer die Adresse der vorherigen Seite, die den Seitenverlauf geöffnet hat. Daher können wir den Ursprungsteil des Links im Referrer verwenden, um den Quelldomänennamen der Anfrage zu ermitteln.
Diese Methode ist nicht narrensicher. Der Wert von Referer wird vom Browser bereitgestellt. Obwohl es klare Anforderungen an das HTTP-Protokoll gibt, gibt es keine Garantie dafür, dass der Browser selbst keine Sicherheitslücken aufweist. . Die Methode zur Überprüfung des Referrer-Werts hängt von der Drittpartei (d. h. dem Browser) ab, um die Sicherheit zu gewährleisten. Theoretisch ist dies nicht sehr sicher. In einigen Fällen können Angreifer den von ihnen angeforderten Referrer verbergen oder sogar ändern.
Strategiename | Attributwert (neu) | |
---|---|---|
Kein Referrer | kein Referrer | |
Kein Empfehlungsgeber Herunterladen | -||
unsichere URL | immer | |