<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[מדריכים]]></title><description><![CDATA[מדריכים]]></description><link>https://tchumim.com/category/14</link><generator>RSS for Node</generator><lastBuildDate>Tue, 21 Apr 2026 17:03:56 GMT</lastBuildDate><atom:link href="https://tchumim.com/category/14.rss" rel="self" type="application/rss+xml"/><pubDate>Sun, 11 Sep 2022 08:12:04 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[מיזוג דואר שמירת קובץ PDF נפרד לכל רשומה]]></title><description><![CDATA[<p dir="auto">שלום לכולם<br />
התבקשתי רבות מחברים פיתרון לבעיה הידועה לבצע מיזוג דואר, אך לשמור קובץ PDF נפרד לכל רשומה, עם שם מותאם אישית.</p>
<p dir="auto">אפרט כאן במדריך שלב אחר שלב איך לבצע זאת, תהיו איתי עד הסוף מקווה שתהנו...</p>
<p dir="auto">נתחיל...</p>
<p dir="auto"><strong>שלב א:</strong></p>
<p dir="auto">ראשית בקובץ ה- Excel של רשימת הנמענים, הוסיפו לטבלת הנתונים ארבעה עמודות בשמות כדלהלן (חשוב שהשמות יהיו מדויקים ללא רווחים מיותרים - לתשומת ליבכם):</p>
<ul>
<li>
<p dir="auto">DocFolderPath</p>
</li>
<li>
<p dir="auto">DocFileName</p>
</li>
<li>
<p dir="auto">PdfFolderPath</p>
</li>
<li>
<p dir="auto">PdfFileName</p>
</li>
</ul>
<p dir="auto"><strong>שלב ב:</strong><br />
צרו שתי תיקיות נפרדות, אחד לקבצי הפלט בפורמט docx, ואחד לקבצי הקלט בפורמט pdf, העתיקו את נתיב התיקייה של קבצי ה- docx והדביקו אותם עבור כל רשומה בשדה שיצרתם בשם DocFolderPath, לאחמ"כ חזרו על הפעולה והפעם העתיקו את נתיב התיקייה של קובצי ה- PDF והדביקו בשדה PdfFolderPath.<br />
בשדה <strong>DocFileName</strong> כתבו את השם של הקובץ עבור הרשומה - ניתן להשתמש בנוסחאות, כמו"כ בשדה <strong>PdfFileName</strong> כתבו את שם הקובץ כנ"ל.</p>
<p dir="auto"><strong>שלב ג:</strong><br />
פתחו את קובץ ה- word והשלימו את פעולת המיזוג כרגיל, עצבו את המסמך כרצונכם.</p>
<p dir="auto"><strong>שלב ד:</strong><br />
פתחו את לשונית מפתחים בקובץ ה- word פתחו את עורך הקוד הוסיפו מודל חדש מצו"ב צילום מסך:<br />
<img src="/assets/uploads/files/1662883665514-3eb2538f-9ab1-41eb-a1df-452212916da6-image.png" alt="3eb2538f-9ab1-41eb-a1df-452212916da6-image.png" class=" img-fluid img-markdown" /></p>
<p dir="auto">הדביקו את הקוד הבא:</p>
<pre><code>Sub MailMergeToPdfBasic()                                                        ' Mark the start of the Subroutine (i.e. Macro) and name it "MailMergeToPdf"
' Macro created by Imnoss Ltd
' Please share freely while retaining attribution
' Last Updated 2021-05-03
    Dim masterDoc As Document, singleDoc As Document, lastRecordNum As Long   ' Create variables ("Post-it Notes") for later use
    Set masterDoc = ActiveDocument                                               ' Identify the ActiveDocument (foremost doc when Macro run) as "masterDoc"

    masterDoc.MailMerge.DataSource.ActiveRecord = wdLastRecord                   ' jump to the last active record (active = ticked in edit recipients)
    lastRecordNum = masterDoc.MailMerge.DataSource.ActiveRecord                  ' retrieve the record number of the last active record so we know when to stop

    masterDoc.MailMerge.DataSource.ActiveRecord = wdFirstRecord                  ' jump to the first active record (active = ticked in edit recipients)
    Do While lastRecordNum &gt; 0                                                   ' create a loop, lastRecordNum is used to end the loop by setting to zero (see below)
        masterDoc.MailMerge.Destination = wdSendToNewDocument                    ' Identify that we are creating a word docx (and no e.g. an email)
        masterDoc.MailMerge.DataSource.FirstRecord = masterDoc.MailMerge.DataSource.ActiveRecord              ' Limit the selection to just one document by setting the start ...
        masterDoc.MailMerge.DataSource.LastRecord = masterDoc.MailMerge.DataSource.ActiveRecord               ' ... and end points to the active record
        masterDoc.MailMerge.Execute False                                        ' run the MailMerge based on the above settings (i.e. for one record)
        Set singleDoc = ActiveDocument                                           ' Identify the ActiveDocument (foremost doc after running the MailMerge) as "singleDoc"
        singleDoc.SaveAs2 _
            FileName:=masterDoc.MailMerge.DataSource.DataFields("DocFolderPath").Value &amp; Application.PathSeparator &amp; _
                masterDoc.MailMerge.DataSource.DataFields("DocFileName").Value &amp; ".docx", _
            FileFormat:=wdFormatXMLDocument                                      ' Save "singleDoc" as a word docx with the details provided in the DocFolderPath and DocFileName fields in the MailMerge data
        singleDoc.ExportAsFixedFormat _
            OutputFileName:=masterDoc.MailMerge.DataSource.DataFields("PdfFolderPath").Value &amp; Application.PathSeparator &amp; _
                masterDoc.MailMerge.DataSource.DataFields("PdfFileName").Value &amp; ".pdf", _
            ExportFormat:=wdExportFormatPDF                                      ' Export "singleDoc" as a PDF with the details provided in the PdfFolderPath and PdfFileName fields in the MailMerge data
        singleDoc.Close False                                                    ' Close "singleDoc", the variable "singleDoc" can now be used for the next record when created
        If masterDoc.MailMerge.DataSource.ActiveRecord &gt;= lastRecordNum Then     ' test if we have just created a document for the last record
            lastRecordNum = 0                                                    ' if so we set lastRecordNum to zero to indicate that the loop should end
        Else
            masterDoc.MailMerge.DataSource.ActiveRecord = wdNextRecord           ' otherwise go to the next active record
        End If

    Loop                                                                         ' loop back to the Do start
End Sub                                                                          ' Mark the end of the Subroutine
</code></pre>
<p dir="auto"><strong>שלב ה וסיום:</strong><br />
סגרו את עורך הקוד.<br />
לחצו על כפתור פקודות מאקרו שבכרטיסיית מפתחים, בחרו את המאקרו בשם <strong>MailMergeToPdfBasic</strong> ולחצו הפעל מצו"ב צילום מסך<br />
<img src="/assets/uploads/files/1662883849719-3890ce69-c0e9-4f30-89ce-3e97b7de750b-image.png" alt="3890ce69-c0e9-4f30-89ce-3e97b7de750b-image.png" class=" img-fluid img-markdown" /></p>
<p dir="auto">כעת שבו בנחת והמתינו עד ליצירת כל הקבצים, להנאתכם תפתחו את תיקיות הפלט שיצרתם וגלו שהיא מלאה קבצים קובץ לכל רשומה בשם המתאים שהגדרתם לה.</p>
<p dir="auto"><a href="https://imnoss.com/word-mail-merge-to-separate-pdfs/" target="_blank" rel="noopener noreferrer nofollow ugc">מקור</a></p>
]]></description><link>https://tchumim.com/topic/13973/מיזוג-דואר-שמירת-קובץ-pdf-נפרד-לכל-רשומה</link><guid isPermaLink="true">https://tchumim.com/topic/13973/מיזוג-דואר-שמירת-קובץ-pdf-נפרד-לכל-רשומה</guid><dc:creator><![CDATA[katz]]></dc:creator><pubDate>Sun, 11 Sep 2022 08:12:04 GMT</pubDate></item><item><title><![CDATA[טיפים לכתיבת שרת נוד ב TS]]></title><description><![CDATA[@צדיק-תמים אמר בטיפים לכתיבת שרת נוד ב TS:

@יוסף-בן-שמעון למה לא לכתוב בtsconfig
        "outDir": "dist"

וכך הקבצים ייווצרו מלכתחילה בתקיה ייעודית? 

תלוי בסביבה ובדרישות, לא מתאים בכל מצב, ובכל מקרה, גם את התיקיה הייעודית כדאי להסתיר
]]></description><link>https://tchumim.com/topic/13410/טיפים-לכתיבת-שרת-נוד-ב-ts</link><guid isPermaLink="true">https://tchumim.com/topic/13410/טיפים-לכתיבת-שרת-נוד-ב-ts</guid><dc:creator><![CDATA[יוסף בן שמעון]]></dc:creator><pubDate>Sun, 05 Jun 2022 23:31:57 GMT</pubDate></item><item><title><![CDATA[מדריך | כתיבת סקריפט צד לקוח עבור אתר NodeBB - שימוש בhooks]]></title><description><![CDATA[בפוסטים הקודמים כתבתי רק על האזנה לאירועים של NodeBB בצד הלקוח.
אלא שניתן גם ליזום אירועים, וכך ניתן לבצע פעולות בממשק בצורה נקיה, ללא צורך בדימוי לחיצות ושאר שטיקים מכוערים...
לדוגמה אם אני רוצה לפתוח נושא חדש (זה רק דוגמה, ספציפית בזה יש את app.newTopic), אני לא צריך לדמות לחיצה על כפתור פתח נושא, ואז לדמות לחיצה על בורר הקטגוריות, וכן הלאה... 
אני יכול פשוט לקרוא לאירוע action:composer.topic.new (מאיפה יש לי אותו? מהתיעוד הרשמי) עם הפרמטרים הנכונים,
ואיך אני יידע איזה פרמטרים?  פשוט מאזינים להוק הרלוונטי ומפעילים אותו בממשק, ורואים בקונסולה איזה פרמטרים הועברו אליו... אפשר גם להיעזר בסקריפט שהבאתי בפוסט הקודם 
לדוגמה כדי להאזין להוק של יצירת נושא:
$(window).on('action:composer.topic.new', (event, data) =&gt; {
    console.log(data);
});

אם תאזינו כך להוק של פתיחת נושא, תוכלו לראות שהוא מקבל אובייקט שמכיל cid ומערך של tags, שבמקרה הזה הם ריקים:
{
    "cid": 0,
    "tags": []
}

וממילא ברגע שנקרא להוק בצורה הזאת:
$(window).trigger('action:composer.topic.new', { 
    cid: "9",
    tags: [
        'test', 'test2'
    ]
 });

נראה שנפתח מייד חלון כתיבת נושא חדש, כאשר ב"קטגוריה" כבר נבחרה קטגוריה מספר 9 - בניה ושיפוצים, ובמקום המיועד כבר הוכנסו התגיות test וtest2:
[image: 1656332912513-fb1681dd-ada4-4a4d-b197-9bba5e29f2a0-image.png]
ותן לחכם ויחכם עוד... 
]]></description><link>https://tchumim.com/topic/12619/מדריך-כתיבת-סקריפט-צד-לקוח-עבור-אתר-nodebb-שימוש-בhooks</link><guid isPermaLink="true">https://tchumim.com/topic/12619/מדריך-כתיבת-סקריפט-צד-לקוח-עבור-אתר-nodebb-שימוש-בhooks</guid><dc:creator><![CDATA[צדיק תמים]]></dc:creator><pubDate>Thu, 20 Jan 2022 15:33:42 GMT</pubDate></item><item><title><![CDATA[בקשה להמלצות על ערוצים&#x2F;סרטונים של תכנות והמסתעף]]></title><description><![CDATA[https://aosabook.org/en/index.html
https://tutsplus.com/
https://www.sitepoint.com/
https://qat.com/top-10-websites-to-learn-web-development-in-2023/
]]></description><link>https://tchumim.com/topic/12462/בקשה-להמלצות-על-ערוצים-סרטונים-של-תכנות-והמסתעף</link><guid isPermaLink="true">https://tchumim.com/topic/12462/בקשה-להמלצות-על-ערוצים-סרטונים-של-תכנות-והמסתעף</guid><dc:creator><![CDATA[chagold]]></dc:creator><pubDate>Tue, 21 Dec 2021 13:14:32 GMT</pubDate></item><item><title><![CDATA[הורדת קבצים מגוגל דרייב (הפרטי) באמצעות google api על ידי nodejs]]></title><description><![CDATA[@חוקר


אם אתה משתמש ב credentials.installed; ולא ב credentials.web; אז הקוד יגיע לך כטקסט להעתקה.


אם יש את זה:
'https://www.googleapis.com/auth/drive'
לא צריך את כל השאר.


כדאי לזכור שלהרבה שימושים service-account גם מספיק, והרבה יותר קל מאשר כל התהליך של OAuth.


]]></description><link>https://tchumim.com/topic/11070/הורדת-קבצים-מגוגל-דרייב-הפרטי-באמצעות-google-api-על-ידי-nodejs</link><guid isPermaLink="true">https://tchumim.com/topic/11070/הורדת-קבצים-מגוגל-דרייב-הפרטי-באמצעות-google-api-על-ידי-nodejs</guid><dc:creator><![CDATA[aaron]]></dc:creator><pubDate>Sun, 18 Apr 2021 21:43:31 GMT</pubDate></item><item><title><![CDATA[Bash Tips: על אנדרואיד ובאש]]></title><description><![CDATA[על אנדרואיד ובאש פרק ב
אחת הסיבות שאני אוהב לשתף מה למדתי היא השיח המעשיר שמגיע לאחר מכן, בקצרה אלו הדברים שלמדתי בעקבות הפוסט שכתבתי על Termux, ותודה רבה לכל נותני ההערות והמעשירים למינם, תבואו לעיתים קרובות יותר 
התקנת Tremux
את Termux לא כדאי להתקין מחנות האפליקציות של גוגל אלא מ Fdroid, הסיבה לכך היא שהמפתחים הפסיקו לעדכן את האפליקציה בגוגל פליי (גרסת SDK ישנה), במקום זאת העדכונים עולים לחנות המקבילה והחופשית.
למי שלא מכיר F-droid היא חנות אפליקציות המקבילה לגוגל פליי, מוכרת מאוד בעולם הקוד פתוח אבל לא רק, שמה הוא בעצם קיצור של FOSS Droid.
תוספי Termux בחינם
לאחר שהתקנתי את החבילה מ Fdroid ראיתי שגם כל התוספים הנלווים ל Termux מוצעים בחינם להורדה, מדובר על תוספים שבתשלום בחנות של גוגל מן הסתם זה עדין כך עקב חוסר העדכון,  תוסף שאהבתי הוא Widget המחזיק רשימת סקריפטים ומאפשר להריץ אותם ישירות ממסך הבית.
כמובן יש עוד, זאת הרשימה.
התממשקות לAPI של המכשיר
בניגוד למה שכתבתי בפוסט הקודם נראה שהתמיכה ב API של אנדרואיד אפילו גדלה, רשימה נאה של פונקציונליות ניתן לראות כאן,
באג בהשלמה אוטומטית
למשתמשי מקלדת samsung יש בעיית התממשקות לTermux, ההשלמה האוטומטית משלימה דיי מה שמתחשק לה, הבעיה ידועה וניתנת לפתרון על ידי הורדת ההערה מהשורה הבאה בקובץ ההגדרות של Termux הלא הוא  .termux/termux.properties
enforce-char-based-input = true

טעינה מחדש של ההגדרות על ידי termux-reload-settings, והסיפור סגור
https://t.me/s/bash_tips
]]></description><link>https://tchumim.com/topic/10994/bash-tips-על-אנדרואיד-ובאש</link><guid isPermaLink="true">https://tchumim.com/topic/10994/bash-tips-על-אנדרואיד-ובאש</guid><dc:creator><![CDATA[trew]]></dc:creator><pubDate>Sun, 04 Apr 2021 18:50:58 GMT</pubDate></item><item><title><![CDATA[האנטומיה של שאילתת SQL]]></title><description><![CDATA[<p dir="auto">אני רוצה לשתף קצת מה שלמדתי לאחרונה על שאילתות SQL. המדריך מיועד למתחילים, למה? כי גם אני מתחיל...<br />
למה אני כותב אותה? א) כי זה עוזר לי ללבן את הנושא. ב) אולי יהיו פה ושם נקודות שגם הותיקים לא הכירו. או שאצליח להאיר את הנושא מזווית שלא חשבו עליו.</p>
<h1>הקדמה ל-SQL ולמדריך</h1>
<p dir="auto">המדריך מדבר על האנטומיה של <em><strong>שאילתות</strong></em> SQL. אני לא הולך להסביר את הצורה שבה שומרים נתונים בטבלאות ויוצרים חיבורים בין טבלאות. אני לא הולך לדבר על המון נושאים לא  פחות חשובים אחרים שקשורים ל-SQL.</p>
<p dir="auto">שפת SQL הינה שפה דקלרטיבית. כלומר, אתה לא אומר למנוע ה-DB <em><strong>מה</strong></em> לעשות. אתה רק מתאר לו <em>מה אתה רוצה לקבל</em> ממנו והוא כבר מחליט לבד מה לעשות.<br />
כתוצאה מכך, אפשר לראות בשאילתת SQL 3 שכבות זו לפנים מזו.<br />
<strong>א)</strong> שכבת התחביר. זו המעטפה, הקליפה, אני לא רוצה להתייחס לזה יותר מדי. (חבל שאי אפשר לחבר שאילתה חוקית מבלי להכיר את התחביר... ועוד יותר חבל שהתחביר משתנה ממנוע למנוע... נקדיש לזה קטע קצר להלן).<br />
<strong>ב)</strong> שכבת השאילתה הלוגית. זו הבקשה שמסתתרת מתחת למילים של השאילתה. אני רוצה להתמקד בשכבה זו. כאשר אתה מייצר שאילתה, אתה קודם כל חושב על שאילתה לוגית, אח"כ אתה מתרגם את זה למילים בשכבת התחביר.<br />
<strong>ג)</strong> שכבת הביצוע. זו הפעולות שאותם המנוע יבצע. לא תמיד מה שביקשת ובסדר שביקשת הוא מה שהמנוע יבצע. הרשות ניתנת למנוע לבצע איזה פעולה שהיא רוצה ובסדר שהיא רוצה ובתנאי שהתוצאה יהיה אותה תוצאה של הפעולה הלוגית שביקשת. אני לא הולך לדבר על נושא זו מכיון שבינתיים אני לא מכיר אותה. נושא זה נחוץ עבור מיטוב ביצועי השאילתה.</p>
<h1>טיפת תחביר</h1>
<p dir="auto">התחביר של שאילתת SQL נראה כך:<br />
<code>SELECT</code> &lt;עמודות...&gt;<br />
<code>FROM</code> &lt;טבלאות...&gt;<br />
<code>WHERE</code> &lt;תנאים&gt;<br />
<code>GROUP BY</code> &lt;ביטוי&gt;<br />
<code>HAVING</code> &lt;תנאים&gt;<br />
<code>ORDER BY</code> &lt;ביטוי&gt;<br />
<code>OFFSET</code> &lt;מספר&gt;<br />
<code>LIMIT</code> &lt;מספר&gt;<br />
(נראה לי שבשני החלקים הנ"ל יש שינויים בין המנועים)<br />
<code>;</code> (לסיום המשפט)</p>
<p dir="auto">כמה נקודות (בלתי אפשרי להקיף פה את הכל, אני רק כותב כמה נקודות):</p>
<ul>
<li>השפה הינה case insensitive, (לא מבדילה בין אותיות גדולות לקטנות). אפשר לכתוב <code>SeLecT</code> גם כן.</li>
<li>שמות הטבלאות והעמודות הם בברירת מחדל case insensitive. תבדקו את התיעוד של המנוע שלכם לגבי יצירת עמודות שהם case sensitive ואיזכורם. ב-postgres אם שם העמודה הינה case sensitive צריך להזכיר את שם העמודה והטבלה בתוך גרשיים (לא ככה: <code>"Table.Column"</code> וגם לא ככה: <code>'Table.Column'</code> או ככה: <code>'Table'.'Column'</code> אלא ככה: <code>‎"Table"."Column"‎</code> - כן כן, מגעיל... בשנות השמונים או השבעים לא ידעו לעשות תחבירים אלגנטיים כנראה...).</li>
<li>לא כל החלקים חיוביים. בעיקרון אפשר להשמיט את הכל חוץ מה-<code>SELECT</code>. כל השאר הם אופצינאליים לפחות בחלק מהמקרים. חלק מהם הם חיוביים במקרים מסויימים. (עזרתי מאוד, לא? הכללים הם הגיוניים ולא קשים לניחוש אחרי שאתה מכיר את המבנה של השאילתה שנרחיב עליו בקטע הבא).</li>
</ul>
<h1>השאילתה הלוגית</h1>
<p dir="auto">כאן הגענו לבשר...<br />
צריך להבין שמה שאתה בעצם עושה בשאילתת SQL היא יצירת קו ייצור שבצד האחד שלו אתה שופך טבלה גולמית, באמצע אתה מריץ עליו כמה טרנספורמציות ובצד השני אתה מקבל עוד טבלה. כל שלב בקו הייצור פועל על התוצאה של השלב הקודם. אי אפשר לשנות את סדר הפעולות.</p>
<blockquote>
<p dir="auto"><img src="https://tchumim.com/assets/plugins/nodebb-plugin-emoji/emoji/android/2139.png?v=9d71ebe86e6" class="not-responsive emoji emoji-android emoji--information_source" style="height:23px;width:auto;vertical-align:middle" title=":information_source:" alt="ℹ" />  חשוב לזכור, הסדר של הטרנספורמציות הם לא בהכרח בסדר שבה הם מוצהרים בשכבת התחביר, וגם לא בהכרח הסדר שאותה המנוע ישתמש!!!</p>
</blockquote>
<p dir="auto">סדר הפעולות היא כזאת:</p>
<ul>
<li><code>FROM</code> - בחירת טבלה גולמית (כולל חיבורים עם טבלאות אחרות).</li>
<li><code>WHERE</code> - סינון השורות</li>
<li><code>GROUP BY</code> - קיפול של כמה שורות לתוך שורה אחת</li>
<li><code>HAVING</code> - שוב סינון על השורות המקופלות</li>
<li><code>SELECT</code> - בחירת עמודות מתוך התוצאה של השלבים הקודמים (כולל יצירת עמודות חדשות שמחושבות מהתוצאה של השלבים הקודמים)</li>
<li><code>DISTINCT</code> - מחיקת כפלויות</li>
<li><code>UNION</code> - חיבור תשובות משאילתה אחרת</li>
<li><code>ORDER BY</code> - מיון השורות</li>
<li><code>OFFSET</code> דילוג לשורה מסויימת</li>
<li><code>LIMIT</code> - מחיקת השורות מה-limit והלאה.</li>
</ul>
<p dir="auto">שוב אני מדגיש, בשכבה 3, כלומר בבצוע בפועל, המנוע חפשי לעשות את הפעולות באיזה סדר שנוח לו. בתנאי קודם למעשה שהתוצאה תהיה אותה תוצאה.</p>
<p dir="auto">עכשיו נפרט קצת על כל שלב.</p>
<h2><code>FROM</code> - בחירת טבלה גולמית</h2>
<p dir="auto">כמה נקודות:</p>
<ul>
<li>שלב זה אופציונאלית. אם משמיטים את השלב הכוונה היא שאנחנו רוצים שהמנוע יחזיר טבלה חדשה יש מאין. צריך להשמיט גם את כל השלבים עד שלב ה-<code>SELECT</code> כי כולם הם פעולות על הטבלה הגולמית - שלא קיימת במקרה זו.<br />
אפשר להשתמש ב-<code>SELECT</code> ערטילאית כמו סוג של <code>echo</code> או <code>console.log</code> כדי לקבל את הערך של ביטוי. לדוגמה <code>SELECT 20+4;‎</code> מחזיר טבלה של 1×1 עם הערך <code>24</code>. או <code>SELECT sqlite_version();‎</code> ב-sqlite מחזיר טבלה של 1×1 עם הערך של הגירסה של המנוע.</li>
<li>ה-<code>FROM</code> מקבלת כל ביטוי שמחזיר טבלה.<br />
ביטויים שמחזירים טבלאות:
<ul>
<li>שם של טבלה, לדוגמה <code>FROM "SomeTable"‎</code></li>
<li>פונקציה שמחזירה טבלה, לדוגמה <code>FROM generate_series(1,100)‎</code> (הפונקציה <code>generate_series</code> ב-postgres מחזירה טבלה - <a href="https://www.postgresql.org/docs/current/functions-srf.html" target="_blank" rel="noopener noreferrer nofollow ugc">[תיעוד]</a>)</li>
<li>שאילתה שמחזירה טבלה, דוגמה: <code>FROM (SELECT * FROM "SomeTable")</code></li>
<li>ביטוי שמחזירה טבלה משולב עם עוד ביטוי שמחזירה טבלה באמצעות <code>JOIN</code></li>
</ul>
</li>
</ul>
<h4><code>JOIN</code> - חיבור כמה טבלאות ביחד</h4>
<p dir="auto">אפשר לחבר כמה טבלאות ביחד על ידי פעולת <code>JOIN</code>.<br />
התחביר של <code>JOIN</code>:</p>
<ul>
<li>&lt;טבלה&gt; (ביטוי שמחזיר טבלה, כנ"ל)</li>
<li><code>JOIN</code> (עם פירוט של סוג ה-<code>JOIN</code>)</li>
<li>&lt;טבלה&gt; (ביטוי שמחזיר טבלה, כנ"ל)</li>
<li><code>ON</code> &lt;תנאי&gt; (או <code>USING</code> &lt;עמודה&gt;)</li>
</ul>
<p dir="auto">הביטוי מחזיר טבלה חדשה שמשלב את שתי הטבלאות המקוריות לפי התנאים שהצבת.</p>
<p dir="auto">יופי, קיבלנו את הטבלה הגולמית, עכשיו נעבור לסינון</p>
<h1><code>WHERE</code> - סינון שורות</h1>
<p dir="auto">התחביר של <code>WHERE</code>:</p>
<ul>
<li><code>WHERE</code> &lt;תנאי&gt;</li>
</ul>
<p dir="auto">זהו!<br />
מהו התנאי? זה ביטוי שמחזיר ערך בוליאני (<code>TRUE</code> או <code>FALSE</code>).<br />
המנוע מעביר את כל השורות דרך התנאי ומוחקת את השורות שלהם הביטוי מחזירה <code>FALSE</code>. כאשר בתוך הביטוי אפשר להזכיר את הערכים של השורה שמועברת דרכה.<br />
דוגמאות:</p>
<ul>
<li><code>WHERE 1</code> - תמיד מחזיר <code>TRUE</code></li>
<li><code>WHERE "SomeColumn" = 25‎‎</code></li>
<li><code>WHERE some_condition() AND another_condition OR something_else()‎</code></li>
</ul>
<p dir="auto">בקיצור הביטויים הם עוצמתיים מאוד, אפשר להוסיף כאן לוגיקה מסובכת</p>
<p dir="auto">אפשר להשמיט לגמרי את ה-<code>WHERE</code> ואז לא מתבצעת סינון</p>
<h1><code>GROUP BY</code> - קיפול כמה שורות לתוך שורה אחת</h1>
<p dir="auto"><strong>התחביר:</strong><br />
<code>GROUP BY</code> &lt;ביטוי שמחזיר עמודה&gt;<br />
<strong>הפעולה:</strong> פעולה זו מקפלת כמה שורות לתוך שורה אחת, מעתה ולהלן לא תוכל לקבל את הערך של שורה ספציפית מתוך השורות המקופלות אלא ערך של פונקציה שמסכמת את כל הפריטים ביחד. לדוגמה סך כולל על ידי פונקציית <code>SUM</code> או ממוצע על ידי פונקציית <code>AVG</code>. או הכי גדול או הכי קטן על ידי פונקציות <code>MIN</code> ו-<code>MAX</code>.</p>
<h1><code>HAVING</code> - שוב סינון</h1>
<p dir="auto"><code>HAVING</code> פועל בדיוק כמו <code>WHERE</code> אלא שכאן אפשר לסנן לפי התוצאה של סיכום השורות שמתקבל על ידי פונקציה מסכמת שמורצת על כל השורות המקופלות באותה שורה.</p>
<h1><code>SELECT</code> - בחירת או יצירת עמודות לטבלה הסופית</h1>
<p dir="auto">סוף סוף קיבלנו את הדאטה הגולמית שאותה אנחנו רוצים להציג, אחרי כל המניפלציות. בשלב זה אתה מגדירים את העמודות שאנחנו רוצים להציג מתוך הדאטה.<br />
אפשר לבחור עמודות קיימות, או אפשר לייצר עמודות חדשות.<br />
לדוגמה: <code>SELECT "SomeColumn", "AnotherColumn", "SomeColumn" * 50 / 2</code> - בחרנו שתי עמודות קיימות, ויצרנו עמודה שלישית שמחושבת מתוך העמודה הראשונה.</p>
<p dir="auto">(כאן ניתן לייצר עמודה שמחושבנת על ידי פונקציית חלון, פונקציות אלו מחזירות ערך שמחושבן גם מכלל השורות ולא רק מהערכים שבשורה הנוחכית. ניתן גם לסנן איזה שורות ישתתפו בחישוב של הפונקציה. איזה כיף!)</p>
<h1><code>DISTINCT</code> - מחיקת כפילויות</h1>
<p dir="auto">אחרי שבחרנו את העמודות נוכל להעביר את התוצאה דרך עוד סינון אחרון אחרון. הסינון הזה מוחקת שורות כפולות לפי עמודה שאתה בוחר.</p>
<h1><code>UNION</code> - חיבור לתשובות של שאילתה אחרת</h1>
<p dir="auto">כאן ניתן לחבר טבלה שקיבלת משאילתה אחרת. השלבים הבאים יחולו על התוצאה של החיבור.</p>
<h1><code>ORDER BY</code> - מיון</h1>
<p dir="auto">ניתן למיין את התוצאות לפי עמודה שאתה בוחר.</p>
<h1><code>LIMIT</code> ו-<code>OFFSET</code></h1>
<p dir="auto">אחרי שיש לנו את כל הדאטה ממויין אפשר להגביל את התשובה לחלק קטן מכלל השורות על ידי <code>LIMIT</code> ו-<code>OFFSET</code>.</p>
<p dir="auto">קרדיטים:</p>
<ul>
<li><a href="https://jvns.ca/blog/2019/10/03/sql-queries-don-t-start-with-select/" target="_blank" rel="noopener noreferrer nofollow ugc">https://jvns.ca/blog/2019/10/03/sql-queries-don-t-start-with-select/</a></li>
<li><a href="https://blog.jooq.org/2016/12/09/a-beginners-guide-to-the-true-order-of-sql-operations/" target="_blank" rel="noopener noreferrer nofollow ugc">https://blog.jooq.org/2016/12/09/a-beginners-guide-to-the-true-order-of-sql-operations/</a></li>
</ul>
<p dir="auto">מקוה שלמדתם משהו.</p>
]]></description><link>https://tchumim.com/topic/9178/האנטומיה-של-שאילתת-sql</link><guid isPermaLink="true">https://tchumim.com/topic/9178/האנטומיה-של-שאילתת-sql</guid><dc:creator><![CDATA[yossiz]]></dc:creator><pubDate>Wed, 17 Jun 2020 10:18:51 GMT</pubDate></item><item><title><![CDATA[שדרוג מראה עורך ה-VBA לערכת נושא VS2019 Dark]]></title><description><![CDATA[@dovid אמר בשדרוג מראה עורך ה-VBA לערכת נושא VS2019 Dark:

https://github.com/rubberduck-vba/Rubberduck/

אני משתמש כל הזמן ב RubberDuck וזה תוספת מבורכת, אבל לא ידוע לי שאפשר להכניס קוד .NET...
]]></description><link>https://tchumim.com/topic/8779/שדרוג-מראה-עורך-ה-vba-לערכת-נושא-vs2019-dark</link><guid isPermaLink="true">https://tchumim.com/topic/8779/שדרוג-מראה-עורך-ה-vba-לערכת-נושא-vs2019-dark</guid><dc:creator><![CDATA[OdedDvir]]></dc:creator><pubDate>Wed, 13 May 2020 11:48:24 GMT</pubDate></item><item><title><![CDATA[אסטריסק: מדריך SIPp]]></title><description><![CDATA[תוך כדי פעולה,
אתה יכול להעלות ולהוריד, ע"י לחיצה על +  העלאה של שיחה אחת, - הורדה של שיחה אחת, * העלאה של 10 שיחות, / הורדה של 10 שיחות.
]]></description><link>https://tchumim.com/topic/8041/אסטריסק-מדריך-sipp</link><guid isPermaLink="true">https://tchumim.com/topic/8041/אסטריסק-מדריך-sipp</guid><dc:creator><![CDATA[MusiCode]]></dc:creator><pubDate>Sat, 29 Feb 2020 18:43:03 GMT</pubDate></item><item><title><![CDATA[מדריך: כתיבת אפליקציות בGO]]></title><description><![CDATA[אתר חביב שמציג בצורה מסודרת ופשוטה את GO ואלו כלים היא מספקת
https://gobyexample.com/
]]></description><link>https://tchumim.com/topic/7940/מדריך-כתיבת-אפליקציות-בgo</link><guid isPermaLink="true">https://tchumim.com/topic/7940/מדריך-כתיבת-אפליקציות-בgo</guid><dc:creator><![CDATA[trew]]></dc:creator><pubDate>Mon, 17 Feb 2020 04:03:03 GMT</pubDate></item><item><title><![CDATA[מימוש עצמי של אירועים]]></title><description><![CDATA[<blockquote>
<p dir="auto">הדרך הטובה ביותר להבין איך מתרחשים אירועים -  היא ליצור אותם בעצמך</p>
</blockquote>
<p dir="auto">אז כדי להבין את המושג האזנה לאירוע, ניסיתי לממש בעצמי מחלקה שמטפלת בנושא.<br />
הדרישה היא – לספק API עם 2 אפשרויות, הרשמה לאירוע והפעלת האירוע, כולל אפשרות להעביר מידע מותאם אישית יחד עם האירוע.<br />
הדרך המתבקשת היא לעבוד עם אוביקט שמכיל מפתחות שהם שמות האירועים, והערך של כל מפתח הוא מערך של פונקציות שהם הקולבקים, וכאשר "יתרחש" האירוע, כלומר כשמישהו יחליט לפלוט אירוע, נעבור בלולאה על המערך ונריץ את כל הקולבקים, ונעביר להם את המידע. האובייקט אמור להיראות כך:</p>
<pre><code>{
    "click": [
        function name (params) {
            ...params
        }
    ],
    "myEvent": [
        function name (params) {
                ...params
            },
        function name (params) {
                ...params
            }
    ]
}
</code></pre>
<p dir="auto">ובכן נתחיל עם המחלקה, בשבל הראשון נחקה את מודל האירועים של נוד, שזה אובייקט גלובלי שכל מי שיש לו גישה אליו יכול להרשם ולפלוט אירועים, ראשית נאתחל נכס פרטי בשם _events שהוא יהיה האובייקט שישמור את כל האירועים והקולבקים. וגם ניצור את המתודה on שדרכה ירשמו לאירועים, מי שרוצה להרשם לאירוע יעביר 2 פרמטרים למתודה on – שם האירוע, והפונקציה שהוא רוצה שתתרחש כשיפלט האירוע</p>
<pre><code>class EventEmitter {
    _events = {};

    on (eventId, callback) {
        this._events[eventId] = this._events[eventId] || [];
        this._events[eventId].push(callback);
    }
}
</code></pre>
<p dir="auto">נבדוק שזה עובד, ניצור מופע של המחלקה, ונרשם להאזנה לאירוע:<br />
<img src="/assets/uploads/files/1580582827095-%D7%AA%D7%9E%D7%95%D7%A0%D7%941.png" alt="תמונה1.png" class=" img-fluid img-markdown" /><br />
ניתן לראות שהנכס הפרטי מכיל את האירוע והקולבק שהעברנו לו.</p>
<p dir="auto">עכשיו נוסיף למחלקה מתודה בשם emit שדרכה יתאפשר להכריז על התרחשות האירוע, היא תקבל גם 2 פרמטרים, שם האירוע והמידע שישלח יחד עם האירוע.</p>
<pre><code>emit (eventId, args) {
       if (!this._events[eventId]) return;
       for (let callback of this._events[eventId]) {
           callback(args)
       }
   }
</code></pre>
<p dir="auto"><img src="/assets/uploads/files/1580582938508-%D7%AA%D7%9E%D7%95%D7%A0%D7%942.png" alt="תמונה2.png" class=" img-fluid img-markdown" /></p>
<p dir="auto">ובכן, זה עובד. כל מי שיש לו גישה ל events יוכל להרשם ולפלוט אירועים.</p>
<hr />
<hr />
<p dir="auto">בשלב השני, נחקה את ההתנהגות של הדפדפן, האירועים מוצמדים לאלמנטים, כל אלמנט DOM מאפשר אירועים פרטיים, לדוגמא כל כפתור פולט אירוע click  כשלוחצים עליו, ואפשר לקבל הודעה על האירוע הפרטי של אלמנט מסוים.<br />
הדרך לעשות את זה פשוטה, נדאג שכל אלמנט יירש מהמחלקה של האירועים. לדוגמא ניצור מחלקה של רכב עם ירושה.</p>
<pre><code>class Car extends EventEmitter {}
</code></pre>
<p dir="auto">כעת ניצור שני סוגי רכבים, ונראה שאפשר ליצור מטפל לכל אירוע מכל רכב בנפרד:<br />
<img src="/assets/uploads/files/1580582984433-7bffb4e0-fc94-4fdd-9001-422bc50e7dfb-image.png" alt="7bffb4e0-fc94-4fdd-9001-422bc50e7dfb-image.png" class=" img-fluid img-markdown" /></p>
]]></description><link>https://tchumim.com/topic/7818/מימוש-עצמי-של-אירועים</link><guid isPermaLink="true">https://tchumim.com/topic/7818/מימוש-עצמי-של-אירועים</guid><dc:creator><![CDATA[יוסף בן שמעון]]></dc:creator><pubDate>Sat, 01 Feb 2020 18:51:30 GMT</pubDate></item><item><title><![CDATA[מדריך: בניית אתרים סטטיים]]></title><description><![CDATA[התקנת hugo (לינוקס)
קודם נוריד את החבילה העדכנית
curl -s https://api.github.com/repos/gohugoio/hugo/releases/latest \
 | grep  browser_download_url \
 | grep Linux-64bit.deb \
 | grep -v extended \
 | cut -d '"' -f 4 \
 | wget -i -

ואז נתקין
sudo dpkg -i hugo*_Linux-64bit.deb

נבדוק שזה הותקן כראוי
hugo --help

ניצור תיקיה בשם hugo שתהיה הסביבת עבודה שלנו
mkdir hugo
cd hugo

וניצור בתוכו את התיקיה שתכיל את האתר שלנו
hugo new site my_site

ונוריד תבנית לאתר (ניתן לבחור תבניות שונות כאן)
git clone https://github.com/calintat/minimal.git my_site/themes/minimal
cp -r themes/minimal/exampleSite/* .

ועכשיו נפעיל את השרת (שימו לב שצריך להחליף את my-url לכתובת של האתר שלכם)
 hugo server -D -b=http://my-url --bind=0.0.0.0

אם הכל נעשה נכון, עכשיו האתר זמין ב http://my-url:1313
ובקיצור
mkdir hugo
cd hugo
hugo new site my_site
git clone https://github.com/calintat/minimal.git my_site/themes/minimal
cp -r themes/minimal/exampleSite/* .
hugo server -D -b=http://my-url --bind=0.0.0.0


]]></description><link>https://tchumim.com/topic/7566/מדריך-בניית-אתרים-סטטיים</link><guid isPermaLink="true">https://tchumim.com/topic/7566/מדריך-בניית-אתרים-סטטיים</guid><dc:creator><![CDATA[nigun]]></dc:creator><pubDate>Wed, 08 Jan 2020 12:49:58 GMT</pubDate></item><item><title><![CDATA[מדריך כתיבת אפליקציה וובית, Full-Stack, צעד אחר צעד]]></title><description><![CDATA[הקדמה:
כעת אני קורא את השיעור הקודם
(למי שמעוניין יש בו את הקוד המלא של איפה שאנחנו אוחזים, מדובר באפליקצייה של דף בודד ותו לא),
ואני רואה שלא ממש גמרנו, צריך גם להראות את הרשימה.
לשם כך אני משנה את המקטע של if (req.url == '/') שזה מתייחס ל"דף הבית" שלנו, ככה:
if (req.url == '/') {
    res.write('Hello To List Page!&lt;br&gt;' +  list.join('&lt;br&gt;') + '&lt;br&gt;&lt;a href="/add-item"&gt;Add Item To List&lt;/a&gt;') ;
}

זה משרשר כמה טקסטים, בתוכם יש קריאה לפונקציה join של מערך (הליסט שלנו), כשהמפריד הוא הbr שזה אלמנט קפיצת שורה בHTML. בסוף על הדרך שמתי לינק (אלמנט a בHTML) לדף הadd-item להוספת פריט חדש.
כעת אפשר להריץ ולראות בהתחלה בדף הבית לינק להוספת פריט.
כעוברים לדף add-item וכשמזינים את הטופס ושלחים מקבלים דף ריק, אם נחזור ידנית לדף הבית נראה את הפריט שהתווסף בהצלחה.
שיעור 7 - שוב על POST וגם על REDIRECT.
הסברתי בעבר שבשביל לשלוח את הטופס לשרת אני משתמש בPOST כי זה בדיוק התפקיד שלו.
למה? זה גורם לפעולה בצד השרת, זה בקשת אינטרנט שיש לה השפעה ולא רק קבלת מידע.
ומה הרווחנו שאנו פועלים לפי הכלל הזה? למשל את התנהגות הדפדפן שבעת ריענון של הדף אחרי השליחה זה יזהיר אותנו מפני פעולה כפולה. בGET זה  יעשה את הפעולה שוב בלי אומר ודברים.
בצד שרת אנחנו יכולים לזהות האם הבקשה היא POST וGET בדיוק כפי שאנו יכולים לבדוק מה הURL. אם כן אנו יכולים להעמיס על URL שכבר בשימוש לGET, כמו כאן שכניסה לadd-item מביאה את הטופס, פעולה נוספת במקרה של POST.
השאלה היא מה קורה אחרי הPOST. אם נחזיר חזרה את הטופס בדיוק כפי שהיה, אז ללקוח יהיה תחושה שלא קרה כלום.
מה שמקובל (כל עוד אנו לא בAJAX - לא להיבהל, יילמד בהמשך) זה או להחזיר את הלקוח לרשימה ואז הוא מבין (וגם רואה) שבקשתו בוצעה.
בפשוטת יכולנו לעשות את זה פשוט - להחזיר בres.write את הרשימה, משהו כזה:
else if (req.url == '/add-item') {
    if (req.method == "POST") {
        parsePostData(req, function (result) {
            list.push(result["the-name"]);
            //בשלב זה אנחנו יכולים לכתוב תשובה ללקוח בדיוק כמו שעשינו בדף הבית
            res.write('Hello To List Page!&lt;br&gt;' +  list.join('&lt;br&gt;') + '&lt;br&gt;&lt;a href="/add-item"&gt;Add Item To List&lt;/a&gt;') ;
        });
    } 

זה לא טוב. למה? כי למשתמש כעת יהיה בשורת הכתובת כתוב add-item והדף בעצם כעת מכיל רשימה. זה גם מאוד "לא נכון" וגם מבלבל, הוא יכול להעתיק את הלינק הזה או לשמור אותו במועדפים מאוחר יותר בלי להתייחס למה כתוב בו, ולהניח שזה לינק לרשימה, שהרי זה מה שהוא רואה.
אז אנחנו צריכים "לשנות את הכתובת בדפדפן" לדף הבית, ובכן זה בלתי אפשרי. מה שעושים זה גורמים לדפדפן לעבור לכתובת של דף הבית כאילו המשתמש לחץ על היפר קישור. עושים את זה ע"י תשובת Redirect.
יש כמה סוגי תשובות REDIRECT, הם מצויינים בקודים 3xx (כלומר 300, 301 וכו'). הסוג שנדרש לנו הוא 303 - See Other. הוא סוג פשוט שאומר, הכל בסדר, כעת תעבור לX.
המבנה של תשובת Redirect בבסיסה רק כותרת אחת ללא כל תוכן:
HTTP/1.1 303 See Other
Location: /

אבל לא נוכל לעשות זאת מייד,
א. כי בקוד שלנו לפני התנאי בכלל כבר שמנו כותרת בשם 'Content-Type', עם HTML, מה שלא מתאים מקרה הזה.
ב. בקוד שלנו שמנו אחרי התנאי res.end שזה אומר לגמור את התשובה ולסגור את החיבור. הבעיה שבמקרה של הpost שלנו שאנו מוסיפים אלמנט לרשימה, הres.end קורה עוד לפני  הוספת האלמנט שכן הוספת האלמנט נעשית כcallback למתודה האסינכרונית parsePostData (כזכור, המתודה parsePostData ניגשת לגוף הבקשה וגישה זו בנויה באופן אסינכרוני = "נודיע לך כזה יקרה", כי הטיפול בבקשה מתחיל עוד לפני שהיא סיימה להגיע).
לשם כך נשנה את הקוד בכמה דברים:
function handleAllRequest(req, res) {
    if (req.url == '/') {
        var page = 'Hello To List Page!&lt;br&gt;' +  list.join('&lt;br&gt;') + '&lt;br&gt;&lt;a href="/add-item"&gt;Add Item To List&lt;/a&gt;';
        sendHtml(res, page) ;
    }
    else if (req.url == '/add-item') {
        if (req.method == "POST") {
            parsePostData(req, function (result) {
                list.push(result["the-name"]);
                res.writeHead(303, { Location: '/' });
                res.end();
            });
        } else {
            sendHtml(res, `&lt;form method="POST"&gt;
                    Enter the item value: &lt;input type="text" name="the-name" &gt;
                    &lt;br&gt;
                    &lt;input type="submit" &gt;
                  &lt;/form&gt;`);
        }
    } else {
        sendHtml(res, 'Opss... Not Found!');
    }
}

function sendHtml(res, str){
    res.setHeader('Content-Type', 'text/html');
    res.end(str);
}

ראשית הסרנו את הres.setHeader והres.end שהיו לפני ואחרי התנאי, כי באחד המקרים של התנאי איננו רוצים את שניהם.
שנית בנינו פונקציה קטנה לשלוח html בתשובה, כדי לחסוך לכתוב שוב ושוב שלושה שורות: res.setHeader, ואז rew.write ולבסוף res.end. בעצם דילגנו על res.write לגמרי גם בפונקציה כי הres.end מקבלת כפרמטר תוכן בדיוק בשביל לחסוך מקרים כאלה (הwrite עושי למקרה של כתיבות רבות לאותה תשובה, במקרה של בודדת אפשר להשתמש בקיצור הזה).
שלישית, וזה הסיבה שעשינו את כל השינויים, הוספנו אחרי הוספת אלמנט (שורות 9-11) הפניה חזרה ל"דף הבית" כלומר לרשימה.
תוכלו כעת לראות אפליקציה לתפארת ששומרת רשימה, אבל כל הרצה הרשימה נמחקת שהרי הכל שמור במשתנה list שבריצת האפליקציה עדיין ריק. אם נרצה לשמור בעולם האמיתי נשתמש כנראה במסד נתונים או בקבצים.
יש לציין שההעברה לרשימה אמנם מקובלת אבל היא לא "100%" מבחינת חוויית משתמש, כיון שיש משתמשים שעד שלא יאמרו להם שזה הצליח, הם לא יהיו בטוחים אם המחשב עשה את מה שהם התכוונו.
בשביל אלו אפשר לעשות העברה לדף אחר, בו כתוב "ההוספה הצליחה!", ומתחת לזה לינק "חזרה לרשימה". יש בזה אבל משהו מייגע עבור יתר המשתמשים. לכן יש כאלה שיעשו שהדף הזה יופיע לשלוש שניות - יהיה כתוב "מעביר אותך לרשימה...". זה בעצם REDIRECT שנעשה בצד הלקוח עם קוד עם השהיית זמן.
יש סיטאוציות שהכי הגיוני זה להישאר באותו הדף של הטופס, למשל אם מטבע הדברים אמורים לשלוח טופס שוב ושוב רצוף (בדוגמה שלנו לשים כמה הפריטים ברשימה). במקרה כזה מחזירים את אותו דף של add-item אבל כותבים איזה חיווי בצד לקוח (למטה או בכותרת צפה זמנית) שהנתונים נשלחו בהצלחה.
]]></description><link>https://tchumim.com/topic/7445/מדריך-כתיבת-אפליקציה-וובית-full-stack-צעד-אחר-צעד</link><guid isPermaLink="true">https://tchumim.com/topic/7445/מדריך-כתיבת-אפליקציה-וובית-full-stack-צעד-אחר-צעד</guid><dc:creator><![CDATA[dovid]]></dc:creator><pubDate>Sat, 28 Dec 2019 21:44:31 GMT</pubDate></item><item><title><![CDATA[פיתוח Nodejs - פרקטיקות מומלצות]]></title><description><![CDATA[<p dir="auto"><a href="https://github.com/goldbergyoni/nodebestpractices" target="_blank" rel="noopener noreferrer nofollow ugc">https://github.com/goldbergyoni/nodebestpractices</a></p>
]]></description><link>https://tchumim.com/topic/7209/פיתוח-nodejs-פרקטיקות-מומלצות</link><guid isPermaLink="true">https://tchumim.com/topic/7209/פיתוח-nodejs-פרקטיקות-מומלצות</guid><dc:creator><![CDATA[dovid]]></dc:creator><pubDate>Tue, 03 Dec 2019 16:11:46 GMT</pubDate></item><item><title><![CDATA[Debug ב NodeJS, עם Google Chrome]]></title><description><![CDATA[<p dir="auto">איך עושים בדיקת באגים עם גוגל כרום:<br />
מפעילים את הסקריפט כך: <code>node --inspect-brk app.js</code>.</p>
<p dir="auto">אם מופיע השגיאה הבאה <code>Starting inspector on 127.0.0.1:9229 failed: address already in use</code>,<br />
צריך לקבוע פורט, כך: <code>node --inspect-brk=1234 app.js</code>.</p>
<p dir="auto">לפתוח בכרום את הכתובת: <a target="_blank" rel="noopener noreferrer nofollow ugc">about:inspect</a>.<br />
אם קבעתם פורט, צריך להכניס אותו לרשימה, כך:<br />
ללחוץ על <code>Open dedicated DevTools for Node</code>, ואח"כ להכניס את הכתובת כך: <img src="/assets/uploads/files/1573824142677-50ef1f18-710b-4cdf-b435-170debba0d18-image.png" alt="50ef1f18-710b-4cdf-b435-170debba0d18-image.png" class=" img-fluid img-markdown" /></p>
<p dir="auto">ללחוץ על הסמל של המופע:<br />
<img src="/assets/uploads/files/1573824229816-33417309-6089-4c06-b1cd-cd0607d1479b-image.png" alt="33417309-6089-4c06-b1cd-cd0607d1479b-image.png" class=" img-fluid img-markdown" /><br />
זהו.</p>
]]></description><link>https://tchumim.com/topic/7039/debug-ב-nodejs-עם-google-chrome</link><guid isPermaLink="true">https://tchumim.com/topic/7039/debug-ב-nodejs-עם-google-chrome</guid><dc:creator><![CDATA[MusiCode]]></dc:creator><pubDate>Fri, 15 Nov 2019 13:24:38 GMT</pubDate></item><item><title><![CDATA[מדריך הקמת מרכזיה טלפונית FreePBX תוך 30 דקות]]></title><description><![CDATA[@nigun הסתדרתי
(פיספסתי בדוקס את ה"יש לבחור סיסמא" 
]]></description><link>https://tchumim.com/topic/4020/מדריך-הקמת-מרכזיה-טלפונית-freepbx-תוך-30-דקות</link><guid isPermaLink="true">https://tchumim.com/topic/4020/מדריך-הקמת-מרכזיה-טלפונית-freepbx-תוך-30-דקות</guid><dc:creator><![CDATA[ש.ב.ח.]]></dc:creator><pubDate>Wed, 12 Dec 2018 19:45:56 GMT</pubDate></item><item><title><![CDATA[RegExp - מדריך מעשי לעבודה עם ביטויים רגולריים בJS]]></title><description><![CDATA[מתודות של String שעובדות עם Regex
כאמור באובייקט סטרינג יש ארבעה מתודות שעובדים עם regex, אני אסכם אותם בקיצור נמרץ:
search - מקבלת טקסט רגיל או ביטוי רגלורי ואם ישנה התאמה כל שהיא היא מחזירה את המיקום שלה. המתודה הזו עשויה למקרים שtest לא מספיק כי אנחנו רוצים לדעת איפה התוצאה, אבל לא חשוב לנו הקבוצות.
split - מפצלת טקסט לאיברי מערך. היא מקבלת טקסט או ביטוי רגולרי.
match - אם הביטוי הוא לא גלובלי, הא מחזירה בדיוק תוצאה זהה לexec - מערך שמייצג את התוצאה הראשונה. אם הוא גלובלי היא מחזירה מערך של כלל התוצאות, אבל רק כטקסט - מפסידים את מידע הקבוצות.
replace - זו המתודה החשובה ביותר שתומכת בביטויים רגולריים.
המתודה הזו מקבלת שתי פרמטרים, הראשון ביטוי לחיפוש והשני ביטוי או פוקנציה מותאמת שתחליף את המופע/ים שיימצאו. היא לא משנה את טקסט המקור אלא מחזירה טקסט חדש.
הפרמטר הראשון יכול להיות טקסט רגיל או ביטוי רגולרי. במידה והפרמטר הראשון הוא טקסט, אז החיפוש הוא תמיד גלובלי - כל התוצאות יוחלפו, ובמידה וזה ביטוי רגולרי זה תלוי בדגל הg - אם הוא איננו זה יחליף רק את המופע הראשון.
פה נגמרת הסקירה ומההודעה הבאה יהיה דוגמאות שימוש.
]]></description><link>https://tchumim.com/topic/2424/regexp-מדריך-מעשי-לעבודה-עם-ביטויים-רגולריים-בjs</link><guid isPermaLink="true">https://tchumim.com/topic/2424/regexp-מדריך-מעשי-לעבודה-עם-ביטויים-רגולריים-בjs</guid><dc:creator><![CDATA[dovid]]></dc:creator><pubDate>Mon, 23 Apr 2018 21:24:49 GMT</pubDate></item><item><title><![CDATA[PM2 - כלי לניהול והרצת אפליקציות טרמינל]]></title><description><![CDATA[אם יש הצעות לכותרת יותר מתאימה - בברכה!
]]></description><link>https://tchumim.com/topic/2190/pm2-כלי-לניהול-והרצת-אפליקציות-טרמינל</link><guid isPermaLink="true">https://tchumim.com/topic/2190/pm2-כלי-לניהול-והרצת-אפליקציות-טרמינל</guid><dc:creator><![CDATA[aaron]]></dc:creator><pubDate>Sat, 07 Apr 2018 23:02:52 GMT</pubDate></item><item><title><![CDATA[Regex - ביטויים רגולריים]]></title><description><![CDATA[@dovid אמר בRegex - ביטויים רגולריים:

בפעם הבאה אני מקוה להתחיל להראות איך לעבוד ספציפית בJS.

פה יש דוגמאות מעשיות
https://reshetech.co.il/regex-in-javascript-tutorial
https://shushan.co.il/הסבר-ולימוד-regex-regular-expression
]]></description><link>https://tchumim.com/topic/1463/regex-ביטויים-רגולריים</link><guid isPermaLink="true">https://tchumim.com/topic/1463/regex-ביטויים-רגולריים</guid><dc:creator><![CDATA[ב.ל]]></dc:creator><pubDate>Tue, 30 Jan 2018 06:48:52 GMT</pubDate></item><item><title><![CDATA[הגמילה מאקסס - סרניטי]]></title><description><![CDATA[@nigun אמר בהגמילה מאקסס - סרניטי:

@משה1
אתה צריך משהו עם מדריכים מפורטים בעברית או שאתה מסתדר גם עם אנגלית?

אנגלית גם
]]></description><link>https://tchumim.com/topic/46/הגמילה-מאקסס-סרניטי</link><guid isPermaLink="true">https://tchumim.com/topic/46/הגמילה-מאקסס-סרניטי</guid><dc:creator><![CDATA[משה1]]></dc:creator><pubDate>Mon, 22 Jan 2018 01:02:13 GMT</pubDate></item></channel></rss>