1+ // Copyright 2019-2025 Chris Mohan, Jaben Cargman
2+ // and GotenbergSharpApiClient Contributors
3+ //
4+ // Licensed under the Apache License, Version 2.0 (the "License");
5+ // you may not use this file except in compliance with the License.
6+ // You may obtain a copy of the License at
7+ //
8+ // http://www.apache.org/licenses/LICENSE-2.0
9+ //
10+ // Unless required by applicable law or agreed to in writing, software
11+ // distributed under the License is distributed on an "AS IS" BASIS,
12+ // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+ // See the License for the specific language governing permissions and
14+ // limitations under the License.
15+
16+ using Newtonsoft . Json . Linq ;
17+
18+ namespace Gotenberg . Sharp . API . Client . Domain . Builders . Faceted ;
19+
20+ public sealed class HtmlConversionBehaviorBuilder
21+ {
22+ private readonly HtmlConversionBehaviors _htmlConversionBehaviors ;
23+
24+ internal HtmlConversionBehaviorBuilder ( HtmlConversionBehaviors htmlConversionBehaviors )
25+ {
26+ _htmlConversionBehaviors = htmlConversionBehaviors ;
27+ }
28+
29+ /// <summary>
30+ /// Sets the wait duration when loading an HTML document before converting it to PDF
31+ /// </summary>
32+ /// <param name="seconds"></param>
33+ /// <returns></returns>
34+ /// <remarks>Prefer <see cref="SetBrowserWaitExpression" /> over waitDelay.</remarks>
35+ public HtmlConversionBehaviorBuilder SetBrowserWaitDelay ( int seconds )
36+ {
37+ _htmlConversionBehaviors . WaitDelay = $ "{ seconds } s";
38+
39+ return this ;
40+ }
41+
42+ /// <summary>
43+ /// Sets a java-script expression to wait before converting an HTML document to PDF until it returns true
44+ /// </summary>
45+ /// <param name="expression">The expression to set</param>
46+ /// <returns></returns>
47+ /// <remarks>Prefer this option over waitDelay.</remarks>
48+ /// <example>SetBrowserWaitExpression("window.status === 'ready'")</example>
49+ /// <exception cref="InvalidOperationException"></exception>
50+ public HtmlConversionBehaviorBuilder SetBrowserWaitExpression ( string expression )
51+ {
52+ if ( expression . IsNotSet ( ) )
53+ {
54+ throw new InvalidOperationException ( "expression is not set" ) ;
55+ }
56+
57+ _htmlConversionBehaviors . WaitForExpression = expression ;
58+
59+ return this ;
60+ }
61+
62+ /// <summary>
63+ /// Overrides the default User-Agent extraHeaders
64+ /// </summary>
65+ /// <param name="userAgent"></param>
66+ /// <returns></returns>
67+ /// <exception cref="InvalidOperationException"></exception>
68+ [ Obsolete ( "Deprecated in Gotenberg v8+" ) ]
69+ public HtmlConversionBehaviorBuilder SetUserAgent ( string userAgent )
70+ {
71+ if ( userAgent . IsNotSet ( ) )
72+ {
73+ throw new InvalidOperationException ( "headerName is not set" ) ;
74+ }
75+
76+ _htmlConversionBehaviors . UserAgent = userAgent ;
77+
78+ return this ;
79+ }
80+
81+ /// <summary>
82+ /// Sets extra HTTP headers that Chromium will send when loading the HTML
83+ /// </summary>
84+ /// <param name="headerName"></param>
85+ /// <param name="headerValue"></param>
86+ /// <returns></returns>
87+ /// <exception cref="InvalidOperationException"></exception>
88+ /// <exception cref="JsonReaderException"></exception>
89+ public HtmlConversionBehaviorBuilder AddAdditionalHeaders ( string headerName , string headerValue )
90+ {
91+ var header = string . Format ( "{0}{2}{1}" , "{" , "}" , $ "{ '"' } { headerName } { '"' } : { '"' } { headerValue } { '"' } ") ;
92+
93+ return AddAdditionalHeaders ( JObject . Parse ( header ) ) ;
94+ }
95+
96+ /// <summary>
97+ /// Sets extra HTTP headers that Chromium will send when loading the HTML
98+ /// </summary>
99+ /// <param name="extraHeaders"></param>
100+ /// <returns></returns>
101+ /// <exception cref="InvalidOperationException"></exception>
102+ public HtmlConversionBehaviorBuilder AddAdditionalHeaders ( JObject extraHeaders )
103+ {
104+ if ( extraHeaders == null )
105+ {
106+ throw new InvalidOperationException ( "extraHeaders is null" ) ;
107+ }
108+
109+ _htmlConversionBehaviors . ExtraHeaders = extraHeaders ;
110+
111+ return this ;
112+ }
113+
114+ /// <summary>
115+ /// Adds a cookie to store in the Chromium cookie jar.
116+ /// </summary>
117+ /// <param name="cookie">The cookie to add</param>
118+ /// <returns></returns>
119+ /// <exception cref="ArgumentNullException"></exception>
120+ public HtmlConversionBehaviorBuilder AddCookie ( Cookie cookie )
121+ {
122+ if ( cookie == null )
123+ {
124+ throw new ArgumentNullException ( nameof ( cookie ) ) ;
125+ }
126+
127+ _htmlConversionBehaviors . Cookies ??= new List < Cookie > ( ) ;
128+
129+ Cookie . Validate ( cookie ) ;
130+
131+ _htmlConversionBehaviors . Cookies . Add ( cookie ) ;
132+
133+ return this ;
134+ }
135+
136+ /// <summary>
137+ /// Sets the document metadata.
138+ /// Not all metadata are writable. Consider taking a look at https://exiftool.org/TagNames/XMP.html#pdf for an
139+ /// (exhaustive?) list of available metadata.
140+ /// </summary>
141+ /// <param name="dictionary"></param>
142+ /// <returns></returns>
143+ public HtmlConversionBehaviorBuilder SetMetadata ( IDictionary < string , object > dictionary )
144+ {
145+ SetMetadata ( JObject . FromObject ( dictionary ) ) ;
146+
147+ return this ;
148+ }
149+
150+ /// <summary>
151+ /// Sets the document metadata.
152+ /// Not all metadata are writable. Consider taking a look at https://exiftool.org/TagNames/XMP.html#pdf for an
153+ /// (exhaustive?) list of available metadata.
154+ /// </summary>
155+ /// <param name="metadata"></param>
156+ /// <returns></returns>
157+ public HtmlConversionBehaviorBuilder SetMetadata ( JObject metadata )
158+ {
159+ if ( metadata == null )
160+ {
161+ throw new InvalidOperationException ( "metadata is null" ) ;
162+ }
163+
164+ _htmlConversionBehaviors . MetaData = metadata ;
165+
166+ return this ;
167+ }
168+
169+ /// <summary>
170+ /// Tells gotenberg to return a 409 response if there are exceptions in the Chromium console.
171+ /// </summary>
172+ /// <returns></returns>
173+ public HtmlConversionBehaviorBuilder FailOnConsoleExceptions ( )
174+ {
175+ _htmlConversionBehaviors . FailOnConsoleExceptions = true ;
176+
177+ return this ;
178+ }
179+
180+ /// <summary>
181+ /// Configures gotenberg to emulate html loading as screen. By default, it loads it as print
182+ /// </summary>
183+ /// <returns></returns>
184+ public HtmlConversionBehaviorBuilder EmulateAsScreen ( )
185+ {
186+ _htmlConversionBehaviors . EmulatedMediaType = "screen" ;
187+
188+ return this ;
189+ }
190+
191+ /// <summary>
192+ /// Gotenberg 8+ ONLY: Configures gotenberg to not wait for Chromium network to be idle.
193+ /// </summary>
194+ /// <returns></returns>
195+ public HtmlConversionBehaviorBuilder SkipNetworkIdleEvent ( )
196+ {
197+ _htmlConversionBehaviors . SkipNetworkIdleEvent = true ;
198+
199+ return this ;
200+ }
201+
202+ /// <summary>
203+ /// Sets the format of the resulting PDF document
204+ /// </summary>
205+ /// <param name="format"></param>
206+ /// <returns></returns>
207+ /// <exception cref="InvalidOperationException"></exception>
208+ public HtmlConversionBehaviorBuilder SetPdfFormat ( ConversionPdfFormats format )
209+ {
210+ if ( format == default )
211+ {
212+ throw new InvalidOperationException ( "Invalid PDF format specified" ) ;
213+ }
214+
215+ _htmlConversionBehaviors . PdfFormat = format ;
216+
217+ return this ;
218+ }
219+
220+ /// <summary>
221+ /// This tells gotenberg to enable Universal Access for the resulting PDF.
222+ /// </summary>
223+ public HtmlConversionBehaviorBuilder SetPdfUa ( bool enablePdfUa = true )
224+ {
225+ _htmlConversionBehaviors . EnablePdfUa = enablePdfUa ;
226+
227+ return this ;
228+ }
229+ }
0 commit comments