• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 167
  • Last Modified:

Close Insert Page.... (Dreamweaver 8.0)


Hi there!  

The question seems simple...  

I created a certain "page.asp" containing (just) the code to insert data into my Access database. I would like it to CLOSE itself right after it finishes populating the database. In other words, I would NOT like it to redirect to another page (as usual) , I would simply want it to close itself (because it has already been opened "over" another page).

Thank you,
fskilnik.

0
fskilnik
Asked:
fskilnik
  • 9
  • 4
1 Solution
 
RouchieCommented:
Providing that the page has been opened in a pop-up window, you can close it by including this in the BODY tag;

   <% asp code for database insert goes here %>
   <html>
   <body onload="window.close();">
   </body>
   </html>

If it's not in a pop-up window, IE will give a warning that the window is trying to close, and Firefox simply does nothing.
0
 
fskilnikAuthor Commented:

Hello, Rouchie.  Thanks for the reply.

I tried your suggestion and it worked but...

The page has been opened in a pop-up but, because of the command suggested, it closes BEFORE I was able to put the data to be updating my database.

Explaining better: there is a certain page A with a button "NEW" (stock transaction). When the user clicks it, it properly opens a pop-up window that has a form in it to be able to populate a certain database.  What I would like to do is to close this pop-up AFTER I press the "Insert Record" button... got it?!

Thanks a lot and sorry for the misunderstanding.  I will wait your expert answer, for sure.

Regards,
Fábio.
0
 
RouchieCommented:
Fábio, no problem, this is also possible.
Is the form posting back to the same page?  i.e. does page1.asp post back to page1.asp where the insert takes place?

If so, you can make the form post back to the same page, but add a querystring on the URL, like this:

<form method="post" action="page1.asp?posted=true">
  <... normal form code here ...>
</form>


then above that where the body tag appears, you write the body tag based on the querystring:
  <% if request.querystring("posted") = true then %>
        <body onload="window.close();">
  <% else %>
        <body>
  <% end if %>


What's happening then is this:   If the page is first loaded, the URL in the browser window will be just PAGE1.ASP and your form will load.  When the form is submitted, the URL will change to PAGE1.ASP?POSTED=TRUE and an alternative <BODY> tag will be written that instantly closes the window.
0
Upgrade your Question Security!

Add Premium security features to your question to ensure its privacy or anonymity. Learn more about your ability to control Question Security today.

 
fskilnikAuthor Commented:

Hi there Rouchie!

Thanks for the very detail answer. I got 100% the picture. Very creative, by the way.

I must be stupid but... I could not put your solution to work, because my form tag (and almost all the insertion code) is Dreamweaver  generated, therefore it is exactly as

<form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1">

I tried to enter the " MM_editAction " arena, I made several alterations but none worked. Some did nothing, some got errors...  To try to help you to help me, here are some extracts of my code where I think could be the place(s) where something should be altered. Please tell me how to change it (or them) or, if none of them are related to it, where should I make the changes.

I guess it´s time I study some ASP and ASP.NET more seriously, to avoid using some automatic (but too obscure) Dreamweaver´s resources, by the way... I have already ordered from Amazon. 2 ASP.NET books. Let´s see!!  :)

Thanks a lot,
Fábio.

P.S.: I have increased this question to 500 points. Not only because it´s getting harder than expected (more work to you, unfortunately) , but also because I made an extra "refresh page" addition to my original necessity.  :)   Please see below.


---------------  Extracts  ---------------------------

01.  At the end of the form:  ("insEqtyTransaction.asp" page is the pop-up page)

<input type="hidden" name="MM_insert" value="form1">
</form>


02.

If (CStr(Request("MM_insert")) = "form1") Then

  MM_editConnection = MM_connSPECIFICNAME_STRING
  MM_editTable = "tblEqtyTransactions"
  MM_editRedirectUrl = "insEqtyTransaction.asp"             <<--------------- This page should close after the insertion

***  Extra thing, Rouchie...  Could we redirect to the "ViewStocksPosition.asp"  (the one that opened the pop-up page) instead, after closing the "insEqtyTransaction.asp" and in a way that the  "ViewStocksPosition.asp" was refreshed? This is important because the user could see the inclusion "at real time" , at the same page he was before pressing the button that opened the insertion form/page ...  (I hope I could be clear in all this.)


03.

 ' append the query string to the redirect URL
  If (MM_editRedirectUrl <> "" And Request.QueryString <> "") Then
    If (InStr(1, MM_editRedirectUrl, "?", vbTextCompare) = 0 And Request.QueryString <> "") Then
      MM_editRedirectUrl = MM_editRedirectUrl & "?" & Request.QueryString
    Else
      MM_editRedirectUrl = MM_editRedirectUrl & "&" & Request.QueryString
    End If
  End If


04.

If (Not MM_abortEdit) Then
    ' execute the insert
    Set MM_editCmd = Server.CreateObject("ADODB.Command")
    MM_editCmd.ActiveConnection = MM_editConnection
    MM_editCmd.CommandText = MM_editQuery
    MM_editCmd.Execute
    MM_editCmd.ActiveConnection.Close

    If (MM_editRedirectUrl <> "") Then
      Response.Redirect(MM_editRedirectUrl)
    End If
 End If


 


0
 
fskilnikAuthor Commented:
Ops, I guess another possible place to have something changed is:

MM_editAction = CStr(Request.ServerVariables("SCRIPT_NAME"))
If (Request.QueryString <> "") Then
  MM_editAction = MM_editAction & "?" & Server.HTMLEncode(Request.QueryString)
End If

0
 
fskilnikAuthor Commented:

I am back again... let me clarify what I mean by:

***  Extra thing, Rouchie...  Could we redirect to the "ViewStocksPosition.asp"  (the one that opened the pop-up page) instead, after closing the "insEqtyTransaction.asp" and in a way that the  "ViewStocksPosition.asp" was refreshed? This is important because the user could see the inclusion "at real time" , at the same page he was before pressing the button that opened the insertion form/page ...  (I hope I could be clear in all this.)

Of course if we redirect the "insEqtyTransaction.asp"  page to the "ViewStocksPosition.asp" it will not work as desirable, because the original "ViewStocksPosition.asp" will be "behind" the pop-up window as before, the only difference would be that the pop-up window would be "ViewStocksPosition.asp" (again) instead of "insEqtyTransaction.asp" .  Anyway, although we would have 2 "ViewStocksPosition.asp" pages opened "at the monitor" , the newer would have to close (as asked) but... the older one would still be not refreshed!!

What I really want is the following: the user has the "ViewStocksPosition.asp"  opened "normally", he presses the "New" buttion in it and this makes a pop-up page "insEqtyTransaction.asp" appear in front of the "ViewStocksPosition.asp" page still open. The user uses the "insEqtyTransaction.asp"  page to insert a record in a database and then, when the "insert record" button is pressed, I would like to have this new record inserted, the "insEqtyTransaction.asp"  page closed and the original  "ViewStocksPosition.asp" refreshed, to make the user able to see the new data recently created "there". Uau... I guess that´s all.  

Sorry for the long messages. I simply want to minimize your headaches.  :)

Regards,
Fábio.

0
 
RouchieCommented:
I'm totally confused here by all this extra stuff!  I think because you don't completely understand what Dreamweaver is doing with all it's automatically generated code, you are adding your own logic on top, which isn't needed.

Dreamweaver is actually already doing the suggestion I made where it checks the querystring before using each particular part of logic.  Instead of my first suggestion, try this instead.  This will prevent you having to write your own logic as it uses DW's form posted check that is used elsewhere in your code.

  <% If (Request.QueryString <> "") Then %>
        <body onload="window.close();">
  <% else %>
        <body>
  <% end if %>

If this doesn't work, post your entire page code either into this thread or upload it somewhere as a .txt file.  It will be easier to see the complete logic rather than just snippets.  Once we've got the window close problem sorted, we can redirect the parent window afterwards.
0
 
fskilnikAuthor Commented:

Thanks for the reply, Rouchie.

After your first suggestion, when I realised that your tag line:  <form method="post" action="page1.asp?posted=true">
was to be made from "mine":  <form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1">  
I really tried to modify or to put my logic mixed with Dreamweaver´s but... when I could not succeed I took all out and all snippets I left here were "without my intervention"...  I simply thought that we would need to alter one or two lines from one of them. I was trying to help, just that.

Thanks for the new suggestion. It worked as I would expect, that is, exactly as your <body onload="window.close();">
first suggested: it closed the pop-up page properly but before it was "seen" and filled and used to insert the record to the database!  In other words, your 2nd idea seems to me the one that we need to use but I could not modify it to the Dreamweaver automatic coding!

As you suggested, I put below all the code. The page "as is" below works in the following sense: the "base page" (with the "New" button) is open, the user clicks this button, the pop-up page opens, the user is able to fill it, press "Insert Record" and the database is filled. The problem is
(1) This pop-up page keeps open, "in front of" the base page. We would have to close it AFTER it populates the db ;
(2) After populating the db, the "base page" is not refreshed automatically therefore the user cannot see this last record recently added. (I know it was added because I can "refresh" the page and then, only then, see the new record!)

Sorry for the hard time you are having here and, of course, thanks a lot for your support.  

Regards,
Fábio.

_________________________________________________________________________________________________

<%@ LANGUAGE="VBSCRIPT" LCID=1033 %>
<!--#include file="../../Connections/connNumber2.asp" -->
<!--#include file="../../Connections/connNumber3.asp" -->
<!--#include file="../functions.asp" -->

<%
' *** Edit Operations: declare variables

Dim MM_editAction
Dim MM_abortEdit
Dim MM_editQuery
Dim MM_editCmd

Dim MM_editConnection
Dim MM_editTable
Dim MM_editRedirectUrl
Dim MM_editColumn
Dim MM_recordId

Dim MM_fieldsStr
Dim MM_columnsStr
Dim MM_fields
Dim MM_columns
Dim MM_typeArray
Dim MM_formVal
Dim MM_delim
Dim MM_altVal
Dim MM_emptyVal
Dim MM_i

MM_editAction = CStr(Request.ServerVariables("SCRIPT_NAME"))
If (Request.QueryString <> "") Then
  MM_editAction = MM_editAction & "?" & Server.HTMLEncode(Request.QueryString)
End If

' boolean to abort record edit
MM_abortEdit = false

' query string to execute
MM_editQuery = ""
%>
<%
' *** Insert Record: set variables

If (CStr(Request("MM_insert")) = "form1") Then

  MM_editConnection = MM_connNumber3_STRING
  MM_editTable = "tblEqtyTransactions"
  MM_editRedirectUrl = "insEqtyTransaction.asp"
  MM_fieldsStr  = "TransTypeID|value|TransDate|value|QtyShares|value|PriceShare|value|Comission|value|Comments|value|StockID|value|LastUpdated|value|WhoUserID|value"
  MM_columnsStr = "TransTypeID|none,none,NULL|TransDate|',none,NULL|QtyShares|none,none,NULL|PriceShare|none,none,NULL|Comission|none,none,NULL|Comments|',none,''|StockID|none,none,NULL|LastUpdated|',none,NULL|WhoUserID|none,none,NULL"

  ' create the MM_fields and MM_columns arrays
  MM_fields = Split(MM_fieldsStr, "|")
  MM_columns = Split(MM_columnsStr, "|")
 
  ' set the form values
  For MM_i = LBound(MM_fields) To UBound(MM_fields) Step 2
    MM_fields(MM_i+1) = CStr(Request.Form(MM_fields(MM_i)))
  Next

  ' append the query string to the redirect URL
  If (MM_editRedirectUrl <> "" And Request.QueryString <> "") Then
    If (InStr(1, MM_editRedirectUrl, "?", vbTextCompare) = 0 And Request.QueryString <> "") Then
      MM_editRedirectUrl = MM_editRedirectUrl & "?" & Request.QueryString
    Else
      MM_editRedirectUrl = MM_editRedirectUrl & "&" & Request.QueryString
    End If
  End If
posted=true
End If
%>
<%
' *** Insert Record: construct a sql insert statement and execute it

Dim MM_tableValues
Dim MM_dbValues

If (CStr(Request("MM_insert")) <> "") Then

  ' create the sql insert statement
  MM_tableValues = ""
  MM_dbValues = ""
  For MM_i = LBound(MM_fields) To UBound(MM_fields) Step 2
    MM_formVal = MM_fields(MM_i+1)
    MM_typeArray = Split(MM_columns(MM_i+1),",")
    MM_delim = MM_typeArray(0)
    If (MM_delim = "none") Then MM_delim = ""
    MM_altVal = MM_typeArray(1)
    If (MM_altVal = "none") Then MM_altVal = ""
    MM_emptyVal = MM_typeArray(2)
    If (MM_emptyVal = "none") Then MM_emptyVal = ""
    If (MM_formVal = "") Then
      MM_formVal = MM_emptyVal
    Else
      If (MM_altVal <> "") Then
        MM_formVal = MM_altVal
      ElseIf (MM_delim = "'") Then  ' escape quotes
        MM_formVal = "'" & Replace(MM_formVal,"'","''") & "'"
      Else
        MM_formVal = MM_delim + MM_formVal + MM_delim
      End If
    End If
    If (MM_i <> LBound(MM_fields)) Then
      MM_tableValues = MM_tableValues & ","
      MM_dbValues = MM_dbValues & ","
    End If
    MM_tableValues = MM_tableValues & MM_columns(MM_i)
    MM_dbValues = MM_dbValues & MM_formVal
  Next
  MM_editQuery = "insert into " & MM_editTable & " (" & MM_tableValues & ") values (" & MM_dbValues & ")"

  If (Not MM_abortEdit) Then
    ' execute the insert
    Set MM_editCmd = Server.CreateObject("ADODB.Command")
    MM_editCmd.ActiveConnection = MM_editConnection
    MM_editCmd.CommandText = MM_editQuery
    MM_editCmd.Execute
    MM_editCmd.ActiveConnection.Close

    If (MM_editRedirectUrl <> "") Then
      Response.Redirect(MM_editRedirectUrl)
    End If
  End If

End If
%>

<%
' *** Restrict Access To Page: Grant or deny access to this page
MM_authorizedUsers="Administ"
MM_authFailedURL="../../retry.htm"
MM_grantAccess=false
If Session("MM_Username") <> "" Then
  If (true Or CStr(Session("MM_UserAuthorization"))="") Or _
         (InStr(1,MM_authorizedUsers,Session("MM_UserAuthorization"))>=1) Then
    MM_grantAccess = true
  End If
End If
If Not MM_grantAccess Then
  MM_qsChar = "?"
  If (InStr(1,MM_authFailedURL,"?") >= 1) Then MM_qsChar = "&"
  MM_referrer = Request.ServerVariables("URL")
  if (Len(Request.QueryString()) > 0) Then MM_referrer = MM_referrer & "?" & Request.QueryString()
  MM_authFailedURL = MM_authFailedURL & MM_qsChar & "accessdenied=" & Server.URLEncode(MM_referrer)
  Response.Redirect(MM_authFailedURL)
End If
%>
<%
Dim rsActivityTypes
Dim rsActivityTypes_numRows

Set rsActivityTypes = Server.CreateObject("ADODB.Recordset")
rsActivityTypes.ActiveConnection = MM_connNumber3_STRING
rsActivityTypes.Source = "SELECT * FROM tblActivityTypes ORDER BY Type ASC"
rsActivityTypes.CursorType = 0
rsActivityTypes.CursorLocation = 2
rsActivityTypes.LockType = 1
rsActivityTypes.Open()

rsActivityTypes_numRows = 0
%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
<title>SVF Blog: Add Eqty Transaction</title>
<link href="../../codes/Style.css" rel="stylesheet" type="text/css" />
</head>
<form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1">
  <table width="659" align="center">
    <tr valign="baseline">
      <td width="80" align="right" nowrap class="BlogStockProfile"><div align="right">Activity</div></td>
      <td width="6" align="right" nowrap>&nbsp;</td>
      <td><select name="TransTypeID">
        <option value="">--- Please select --- </option>
        <%
While (NOT rsActivityTypes.EOF)
%><option value="<%=(rsActivityTypes.Fields.Item("ActivityID").Value)%>"><%=(rsActivityTypes.Fields.Item("Type").Value)%></option>
        <%
  rsActivityTypes.MoveNext()
Wend
If (rsActivityTypes.CursorType > 0) Then
  rsActivityTypes.MoveFirst
Else
  rsActivityTypes.Requery
End If
%>
      </select></td>
      <td class="BlogStockProfile"><div align="right">Date</div></td>
      <td>&nbsp;</td>
      <td><input type="text" name="TransDate" value="<%=Date() %>" size="15" /></td>
    </tr>
    <tr valign="baseline">
      <td align="right" nowrap class="BlogStockProfile"><div align="right"># Shares</div></td>
      <td align="right" nowrap>&nbsp;</td>
      <td width="154"><input type="text" name="QtyShares" value="" size="19" /></td>
      <td width="136" class="BlogStockProfile"><div align="right">Price/Share</div></td>
      <td width="9">&nbsp;</td>
      <td width="246"><input type="text" name="PriceShare" value="" size="15" /></td>
    </tr>
    <tr valign="baseline">
      <td align="right" nowrap class="BlogStockProfile"><div align="right">Comission</div></td>
      <td align="right" nowrap>&nbsp;</td>
      <td><input type="text" name="Comission" value="" size="19," /></td>
      <td colspan="2">&nbsp;</td>
      <td>&nbsp;</td>
    </tr>
    <tr valign="baseline">
      <td align="right" nowrap class="BlogStockProfile"><div align="right">Memo</div></td>
      <td align="right" nowrap>&nbsp;</td>
      <td colspan="4"><input type="text" name="Comments" value="" size="67" /></td>
    </tr>
    <tr valign="baseline">
      <td align="right" nowrap class="BlogStockProfile">&nbsp;</td>
      <td align="right" nowrap>&nbsp;</td>
      <td colspan="4">&nbsp;</td>
    </tr>
   
    <tr valign="baseline">
      <td colspan="2" align="right" nowrap>&nbsp;</td>
      <td><div align="center"></div></td>
      <td><input name="submit" type="submit" value="Insert record" /></td>
      <td colspan="2">&nbsp;</td>
    </tr>
  </table>
  <input type="hidden" name="StockID" value="<%= Request.QueryString("StockID") %>" />
  <input type="hidden" name="LastUpdated" value="<%= Date() %>" />
<input type="hidden" name="WhoUserID" value="<%= Session("UserIDLog")  %>"id")" size="32" />
<input type="hidden" name="MM_insert" value="form1">
</form>
<p>
<%
%>
</p>
</body>
</html>
<%
rsActivityTypes.Close()
Set rsActivityTypes = Nothing
%>
0
 
RouchieCommented:
Your biggest problem here is that there is no <BODY> tag.  Its a wonder the code ever appeared at all!

Change this block of your existing code:

     <title>SVF Blog: Add Eqty Transaction</title>
     <link href="../../codes/Style.css" rel="stylesheet" type="text/css" />
     </head>
     <form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1">

to say this (paste straight over the top):

     <title>SVF Blog: Add Eqty Transaction</title>
     <link href="../../codes/Style.css" rel="stylesheet" type="text/css" />
     <script language="javascript" type="text/javascript">
         function refreshAndClose() {
            opener.window.location.reload(1);
            window.close();
         }
     </script>
     </head>
     <% if request.QueryString("post") = "post" then %>
          <body onload="refreshAndClose();">
     <% else %>
          <body>
     <% end if %>
     <form ACTION="<%=MM_editAction%>?post=post" METHOD="POST" name="form1">

0
 
fskilnikAuthor Commented:

> Your biggest problem here is that there is no <BODY> tag.  Its a wonder the code ever appeared at all!

You are right, Rouchie. When I took your suggestion out (before printing here all the code) , I forgot to leave the original <body> tag but, yes, incredible, it still works without it.

Thanks for the detail suggestion. It still doesn´t work, unfortunately. The "Insert Record" works, but the back-page does not refresh nor the pop-up window closes.

When I changed the

 <% if request.QueryString("post") = "post" then %>
         <body onload="refreshAndClose();">
     <% else %>
         <body>
     <% end if %>

part to

<% if request.QueryString("post") = "post" then %>
         <body onload="refreshAndClose();">
     <% else %>
        <body onload="refreshAndClose();">               <<----------------------------- Here
     <% end if %>

I realized that the pop-up closes and the back-page seems to refresh (that´s what we need!) but, of course, before I have "time" to fill the pop-up insertion form.

I mention this try because it may help you guess what´s slightly inadequate in this new suggestion.

Thanks for all your good-will,

Fábio.

0
 
fskilnikAuthor Commented:

Good news, Rouchie!

I managed to adapt your code to the following:

<title>SVF Blog: Add Eqty Transaction</title>
     <link href="../../codes/Style.css" rel="stylesheet" type="text/css" />
     <script language="javascript" type="text/javascript">
         function refreshAndClose() {
           opener.window.location.reload(1);
           window.close();        
         }
     </script>
     </head>
     <body>                   <<-------------- No need for that posting!  :)

     <form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1"
        onsubmit="refreshAndClose();">                 <<----------------------------------  because of this!  ;)

The only thing that does not occur satisfactory is that, after pressing the "Insert Record" button, the pop-up page closes and the page seems to refresh but... the new record is not presented at the "base-page". I guess there is nothing wrong because if I press manually the refresh, it works right!  The problem seems to me that I have to put some code in the base-page, not just in the pop-up one!

I will keep trying following this idea.  Please tell me what do you think about all this, ok?!

Thanks a lot,
Fábio.

0
 
fskilnikAuthor Commented:

DONE, Rouchie!  Hurrah!!   :)

Congrats, you made my day!  :)  :)

I put at the EE search the expression  " opener.window.location.reload " and not only I understood what it does (nice!) but I also found at

http://www.experts-exchange.com/Web/Web_Languages/JavaScript/Q_21026615.html?query=opener.window.location.reload%281%29&clearTAFilter=true

a suggestion without the number 1 present at the code above!  I tried without it and that´s it.  It works as expected.  


Thank you very much for your really continuous support.  I hope I have the pleasure to count on you another times.

All the best,
Fábio.

-------------------------------------------------------------------------------------------------------------
Final Code:

<title>SVF Blog: Add Eqty Transaction</title>
     <link href="../../codes/Style.css" rel="stylesheet" type="text/css" />
     <script language="javascript" type="text/javascript">
         function refreshAndClose() {
           opener.window.location.reload();            
           window.close();
         }
     </script>
     </head>
     <body>  
     <form ACTION="<%=MM_editAction%>" METHOD="POST" name="form1"
        onsubmit="refreshAndClose();">

0
 
fskilnikAuthor Commented:

I´m back, Rouchie.  With really good news. Good news at the server, I mean!  ;)

My modifications did NOT work out when I uploaded the page to the server... and then I found an EE solution from sriggumma with EXACTLY the same structure as the one you suggested (the one I clicked as ACCEPTED).

It is here:

http://www.experts-exchange.com/Programming/Programming_Languages/Dot_Net/ASP_DOT_NET/Q_21551709.html?query=opener.window.location.reload&clearTAFilter=true 

The differences between your coding and his are almost none but enough to give me these extra hours of knocking my head at the wall...  :)  Well, the code follows.

Thanks a lot, really. Sorry for all this messages. (For the good part, it "proves" that I am involved with getting it done, right?)

All the best,
Fábio.

-------------------------------------------------------------------------------------------
Really Final Code (works at the Server)

01.  Function definition:

 <script language="javascript">
     <!--
      var bPostedBack = false;
      function RefreshClose()
      {
          if (bPostedBack!=true)
              {
          window.opener.location.reload();
          window.close();
          }
      } // RefreshClose
//-->
</script>

02.  BODY tag and form properties:

*******
</head>
     <body onunload="JavaScript:RefreshClose();">  
     <form ACTION="<%=MM_editAction%>?bPostedBack = true;" METHOD="POST" name="form1">
*******
0

Featured Post

[Webinar] Cloud and Mobile-First Strategy

Maybe you’ve fully adopted the cloud since the beginning. Or maybe you started with on-prem resources but are pursuing a “cloud and mobile first” strategy. Getting to that end state has its challenges. Discover how to build out a 100% cloud and mobile IT strategy in this webinar.

  • 9
  • 4
Tackle projects and never again get stuck behind a technical roadblock.
Join Now