Ampersand not passed in url as encoded character - vba

I am passing a url using a string from a cell in an excel workbook.
The string is : Ben & Jerry's 2017 Base PIC - 1.
The following is my code to pass the string in a url:
Dim targetUrl As String: targetUrl =
"https://catalina.my.salesforce.com/_ui/search/ui/UnifiedSearchResults?searchType=2&sen=aAh&str=" & i & "#!/initialViewMode=summary"
where 'i' is the string that is passed.
This is the url obtained in chrome :
https://catalina.my.salesforce.com/_ui/search/ui/UnifiedSearchResults?str=Ben+&+Jerry%27s+2017+Base+PIC+-+1+=&searchType=2&sen=aAh#!/fen=aAh&initialViewMode=detail&str=Ben
As you can see, the '&' isn't encoded and the search doesn't include any value after 'Ben'.
Could someone guide me on how to solve this issue? Thank you.

To encode the parameter:
Sub Test()
Dim url As String
url = "https://catalina.my.salesforce.com/_ui/search/ui/UnifiedSearchResults" _
& "?searchType=2" _
& "&sen=aAh" _
& "&str=" & EncodeURL("Ben & Jerry's 2017 Base PIC - 1") _
& "#!/initialViewMode=summary"
Debug.Print url
End Sub
Public Function EncodeURL(url As String) As String
Dim buffer As String, i As Long, c As Long, n As Long
buffer = String$(Len(url) * 12, "%")
For i = 1 To Len(url)
c = AscW(Mid$(url, i, 1)) And 65535
Select Case c
Case 48 To 57, 65 To 90, 97 To 122, 45, 46, 95 ' Unescaped 0-9A-Za-z-._ '
n = n + 1
Mid$(buffer, n) = ChrW(c)
Case Is <= 127 ' Escaped UTF-8 1 bytes U+0000 to U+007F '
n = n + 3
Mid$(buffer, n - 1) = Right$(Hex$(256 + c), 2)
Case Is <= 2047 ' Escaped UTF-8 2 bytes U+0080 to U+07FF '
n = n + 6
Mid$(buffer, n - 4) = Hex$(192 + (c \ 64))
Mid$(buffer, n - 1) = Hex$(128 + (c Mod 64))
Case 55296 To 57343 ' Escaped UTF-8 4 bytes U+010000 to U+10FFFF '
i = i + 1
c = 65536 + (c Mod 1024) * 1024 + (AscW(Mid$(url, i, 1)) And 1023)
n = n + 12
Mid$(buffer, n - 10) = Hex$(240 + (c \ 262144))
Mid$(buffer, n - 7) = Hex$(128 + ((c \ 4096) Mod 64))
Mid$(buffer, n - 4) = Hex$(128 + ((c \ 64) Mod 64))
Mid$(buffer, n - 1) = Hex$(128 + (c Mod 64))
Case Else ' Escaped UTF-8 3 bytes U+0800 to U+FFFF '
n = n + 9
Mid$(buffer, n - 7) = Hex$(224 + (c \ 4096))
Mid$(buffer, n - 4) = Hex$(128 + ((c \ 64) Mod 64))
Mid$(buffer, n - 1) = Hex$(128 + (c Mod 64))
End Select
Next
EncodeURL = Left$(buffer, n)
End Function

Related

Error when extract embedded Files from Word

I found a very good solution about extracting embedded files in word. But this solution fails at ExtractFile function with error "subscript out of range" when I extract file. exe or .txt
Please help me.
How to extract embedded Files from Word
Sub ExtractFile(ByVal A0, ByVal A1, ByVal A2, ByVal A3, ByVal A4, ByVal OleFN, ByVal Z0, ByVal Z1, ByVal Z2, ByVal Z3, ByVal Z4, ByVal Z5, ByVal TextFN, ByVal offset, ByVal length)
Dim i, j, nFile As Long
Dim L() As Byte
Dim B() As Byte
If Not FileOpen(OleFN, B) Then Exit Sub
For i = 0 To UBound(B) - 64
If IIf(A0 < 0, B(i) < A0 * -1, B(i) = A0) And IIf(A1 = 256, B(i + 1) > 0, B(i + 1) = A1) And IIf(A2 = 256, B(i + 2) > 0, B(i + 2) = A2) And IIf(A3 = 256, B(i + 3) > 0, B(i + 3) = A3) And IIf(A4 = 256, B(i + 4) > 0, B(i + 4) = A4) Then Exit For
Next
If Z0 < 257 Then
For j = UBound(B) - 16 To i - 64 Step -1
If IIf(Z0 = 256, B(j) > 0, B(j) = Z0) And IIf(Z1 = 256, B(j + 1) > 0, B(j + 1) = Z1) And IIf(Z2 = 256, B(j + 2) > 0, B(j + 2) = Z2) And B(j + 3) = Z3 And IIf(Z4 = 256, B(j + 4) > 0, B(j + 4) = Z4) And IIf(Z5 = 256, B(j + 5) > 0, B(j + 5) = Z5) Then Exit For
Next
Else
j = UBound(B)
End If
ReDim L(0 To j - i + length)
For j = 0 To IIf(UBound(L) + i + offset > UBound(B), UBound(L) + i - length, UBound(L))
L(j) = B(i + j + offset)
Next
nFile = FreeFile
Open TextFN For Binary Access Write As nFile
Put nFile, , L
Close nFile
End Sub
ReDim encountered an error with message: "subscript out of range"

VBA root finding trough bisection

My vba code keeps returning a value of 0 when I know the roots of my function are not 0.
It's pretty simple code but I can't seem to debug it. Any idea where this error might be coming from??
Option Explicit
Public Function Bisect(ByVal xlow As Double, ByVal xhigh As Double) As Double
Dim i As Integer
Dim xmid As Double
xmid = (xlow + xhigh) / 2
For i = 1 To 100
If f(xlow) * f(xmid) < 0 Then
xhigh = xmid
xmid = (xlow + xhigh) / 2
Else
xlow = xmid
xmid = (xlow + xhigh) / 2
End If
Next i
Bisect = xmid
End Function
Function f(ByVal x As Double, Optional ByRef inputArray As Range) As Variant
Dim ca0 As Double
Dim v0 As Double
Dim k As Double
Dim e As Double
Dim ac As Double
Dim L As Double
inputArray(2, 2) = ca0
inputArray(3, 2) = v0
inputArray(4, 2) = k
inputArray(5, 2) = e
inputArray(6, 2) = ac
inputArray(7, 2) = L
f(x) = (v0 / (k * ca0 * ac)) * ((2 * e * (1 + e) * Log(1 - x)) + (e ^ 2 * x) + (((1 + e) ^ 2 * x) / (1 - x))) - L
End Function
' i Think you want to take those constant values from cells presentin the sheet
Function f(ByVal x As Double) As Variant
Dim inputArray As Range
Dim ca0 As Double
Dim v0 As Double
Dim k As Double
Dim e As Double
Dim ac As Double
Dim L As Double
' i Think you want to take values from cells in the sheet
ca0 = ActiveSheet.Cells(2, 2).Value
v0 = ActiveSheet.Cells(3, 2).Value
k = ActiveSheet.Cells(4, 2).Value
e = ActiveSheet.Cells(5, 2).Value
ac = ActiveSheet.Cells(6, 2).Value
L = ActiveSheet.Cells(7, 2).Value
Could it be that you try to assign the inputarray with empty variables?
In my mind it should be:
ca0 = inputArray(2, 2)
v0 = inputArray(3, 2)
And so on.
I'm guessing
f(x) = (v0 / (k * ca0 * ac)) * ((2 * e * (1 + e) * Log(1 - x)) + (e ^ 2 * x) + (((1 + e) ^ 2 * x) / (1 - x))) - L
Should be
f = (v0 / (k * ca0 * ac)) * ((2 * e * (1 + e) * Log(1 - x)) + (e ^ 2 * x) + (((1 + e) ^ 2 * x) / (1 - x))) - L

Formula error after file save from network to local

I have issue with an Excel worksheet that contains the formula:
=Spline($D$9:$D$34,$J$9:$J$34,$D43)
Sheet works fine until I open this sheet on network drive and save it on local drive. Then this formula throws #NAME? error. Strange is, that error is gone when I click on line with formula to edit it and press enter (nothing changes in formula).
Have someone met similar issue?
I just found another information. Formula spline is defined in VBA module, not internal in Excel. It looks like. But issue is still here.
Function spline(periodcol As Range, ratecol As Range, x As Range)
Dim period_count As Integer
Dim rate_count As Integer
period_count = periodcol.Rows.Count
rate_count = ratecol.Rows.Count
If period_count <> rate_count Then
spline = "Error: Range count does not match"
GoTo endnow
End If
ReDim xin(period_count) As Single
ReDim yin(period_count) As Single
Dim c As Integer
For c = 1 To period_count
xin(c) = periodcol(c)
yin(c) = ratecol(c)
Next c
Dim n As Integer
Dim i, k As Integer
Dim p, qn, sig, un As Single
ReDim u(period_count - 1) As Single
ReDim yt(period_count) As Single
n = period_count
yt(1) = 0
u(1) = 0
For i = 2 To n - 1
sig = (xin(i) - xin(i - 1)) / (xin(i + 1) - xin(i - 1))
p = sig * yt(i - 1) + 2
yt(i) = (sig - 1) / p
u(i) = (yin(i + 1) - yin(i)) / (xin(i + 1) - xin(i)) - (yin(i) - yin(i - 1)) / (xin(i) - xin(i - 1))
u(i) = (6 * u(i) / (xin(i + 1) - xin(i - 1)) - sig * u(i - 1)) / p
Next i
qn = 0
un = 0
yt(n) = (un - qn * u(n - 1)) / (qn * yt(n - 1) + 1)
For k = n - 1 To 1 Step -1
yt(k) = yt(k) * yt(k + 1) + u(k)
Next k
Dim klo, khi As Integer
Dim h, b, a As Single
klo = 1
khi = n
Do
k = khi - klo
If xin(k) > x Then
khi = k
Else
klo = k
End If
k = khi - klo
Loop While k > 1
h = xin(khi) - xin(klo)
a = (xin(khi) - x) / h
b = (x - xin(klo)) / h
y = a * yin(klo) + b * yin(khi) + ((a ^ 3 - a) * yt(klo) + (b ^ 3 - b) * yt(khi)) * (h ^ 2) / 6
spline = y
endnow:
End Function
Try to add:
Application.Volatile
to your VBA code. Add this just below the Function statement to force a renewed calculation as soon as anything changes.

The results of my functions when I call a spline function gives wrong values

I have a function that only call the spline function when something happens..in this case when a division is less than zero..the inputs for the function is the same that for the spline function(called CUBIC), the spline was tested and works well when I call it direct! someone can help me?...follows a party of the code
Function NDF6(T As Variant, dias As Variant, taxas As Variant)
If T <= dias(1) Then
NDF6 = taxas(1)
Exit Function
End If
If T >= dias(tam) Then
NDF6 = taxas(tam)
Exit Function
End If
For i = 1 To tam
If T <= dias(i) Then
If taxas(i) / taxas(i - 1) < 0 Then
Call CUBIC(T, dias, taxas)
Else
i0 = ((taxas(i - 1) * dias(i - 1)) / 360) + 1
i1 = ((taxas(i - 1) * dias(i - 1)) / 360) + 1
irel = i1 / i0
i2 = irel ^ ((T - dias(i - 1)) / (dias(i) - dias(i - 1)))
i2rel = i2 * i0
i2real = i2rel - 1
NDF6 = i2real * (360 / T)
End If
Public Function CUBIC(x As Variant, input_column As Variant, output_column As Variant)
The function returns a zero value when I call the cubic function. The inputs are a cell with a value with a value equivalent a day and two arrays(DUONOFF and ONOFF) equivalent a days and rates, I call the function like:
NDF6(512,DUONOFF,ONOFF)
follows the CUBIC function
Public Function CUBIC(x As Variant, input_column As Variant, output_column As Variant)
'Purpose: Given a data set consisting of a list of x values
' and y values, this function will smoothly interpolate
' a resulting output (y) value from a given input (x) value
' This counts how many points are in "input" and "output" set of data
Dim input_count As Integer
Dim output_count As Integer
input_count = input_column.Rows.Count
output_count = output_column.Rows.Count
Next check to be sure that "input" # points = "output" # points
If input_count <> output_count Then
CUBIC = "Something's messed up! The number of indeces number of output_columnues don't match!"
GoTo out
End If
ReDim xin(input_count) As Single
ReDim yin(input_count) As Single
Dim c As Integer
For c = 1 To input_count
xin(c) = input_column(c)
yin(c) = output_column(c)
Next c
values are populated
Dim N As Integer 'n=input_count
Dim i, k As Integer 'these are loop counting integers
Dim p, qn, sig, un As Single
ReDim u(input_count - 1) As Single
ReDim yt(input_count) As Single 'these are the 2nd deriv values
N = input_count
yt(1) = 0
u(1) = 0
For i = 2 To N - 1
sig = (xin(i) - xin(i - 1)) / (xin(i + 1) - xin(i - 1))
p = sig * yt(i - 1) + 2
yt(i) = (sig - 1) / p
u(i) = (yin(i + 1) - yin(i)) / (xin(i + 1) - xin(i)) - (yin(i) - yin(i - 1)) / (xin(i) - xin(i - _1))
u(i) = (6 * u(i) / (xin(i + 1) - xin(i - 1)) - sig * u(i - 1)) / p
Next i
qn = 0
un = 0
yt(N) = (un - qn * u(N - 1)) / (qn * yt(N - 1) + 1)
For k = N - 1 To 1 Step -1
yt(k) = yt(k) * yt(k + 1) + u(k)
Next k
now eval spline at one point
Dim klo, khi As Integer
Dim h, b, a As Single
first find correct interval
klo = 1
khi = N
Do
k = khi - klo
If xin(k) > x Then
khi = k
Else
klo = k
End If
k = khi - klo
Loop While k > 1
h = xin(khi) - xin(klo)
a = (xin(khi) - x) / h
b = (x - xin(klo)) / h
y = a * yin(klo) + b * yin(khi) + ((a ^ 3 - a) * yt(klo) + (b ^ 3 - b) * yt(khi)) * (h ^ 2) _/ 6
CUBIC = y
out:
End Function

Descrypt SagePay string vb.net

I have been having some problems trying to decrypt the string returned back from SagePay.
I used their asp.net kit which included the encrypt and decrypt functions using base64 - sending the information to SagePay is not a problem but I am having a number of problems trying to descrypt the string.
Here is the function I am using to descypt:
Private Function base64Decode(ByVal strEncoded As String) As String
Dim iRealLength As Integer
Dim strReturn As String
Dim iBy4 As Integer
Dim iIndex As Integer
Dim iFirst As Integer
Dim iSecond As Integer
Dim iThird As Integer
Dim iFourth As Integer
If Len(strEncoded) = 0 Then
base64Decode = ""
Exit Function
End If
'** Base 64 encoded strings are right padded to 3 character multiples using = signs **
'** Work out the actual length of data without the padding here **
iRealLength = Len(strEncoded)
Do While Mid(strEncoded, iRealLength, 1) = "="
iRealLength = iRealLength - 1
Loop
'** Non standard extension to Base 64 decode to allow for + sign to space character substitution by **
'** some web servers. Base 64 expects a +, not a space, so convert vack to + if space is found **
Do While InStr(strEncoded, " ") <> 0
strEncoded = Left(strEncoded, InStr(strEncoded, " ") - 1) & "+" & Mid(strEncoded, InStr(strEncoded, " ") + 1)
Loop
strReturn = ""
'** Convert the base 64 4x6 byte values into 3x8 byte real values by reading 4 chars at a time **
iBy4 = (iRealLength \ 4) * 4
iIndex = 1
Do While iIndex <= iBy4
iFirst = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 0, 1)))
'iFirst = CType(System.Convert.ToByte(CType(Mid(strEncoded, iIndex + 0, 1), Char)), Integer)
iSecond = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 1, 1)))
'iSecond = CType(System.Convert.ToByte(CType(Mid(strEncoded, iIndex + 1, 1), Char)), Integer)
iThird = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 2, 1)))
'iThird = CType(System.Convert.ToByte(CType(Mid(strEncoded, iIndex + 2, 1), Char)), Integer)
iFourth = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 3, 1)))
'iFourth = CType(System.Convert.ToByte(CType(Mid(strEncoded, iIndex + 3, 1), Char)), Integer)
strReturn = strReturn + CType(System.Convert.ToChar(((iFirst * 4) And 255) + ((iSecond \ 16) And 3)), String) 'Chr(((iFirst * 4) And 255) + ((iSecond \ 16) And 3))
strReturn = strReturn + CType(System.Convert.ToChar(((iSecond * 16) And 255) + ((iThird \ 4) And 15)), String) 'Chr(((iSecond * 16) And 255) + ((iThird \ 4) And 15))
strReturn = strReturn + CType(System.Convert.ToChar(((iThird * 64) And 255) + (iFourth And 63)), String) 'Chr(((iThird * 64) And 255) + (iFourth And 63))
iIndex = iIndex + 4
Loop
'** For non multiples of 4 characters, handle the = padding **
If iIndex < iRealLength Then
iFirst = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 0, 1)))
iSecond = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 1, 1)))
strReturn = strReturn & Chr(((iFirst * 4) And 255) + ((iSecond \ 16) And 3))
If iRealLength Mod 4 = 3 Then
iThird = arrBase64DecMap(Asc(Mid(strEncoded, iIndex + 2, 1)))
strReturn = strReturn & Chr(((iSecond * 16) And 255) + ((iThird \ 4) And 15))
End If
End If
base64Decode = strReturn
End Function
I don't think the web server is trying to encode anything as there are no + symbols within the url string and I have just glanced over the two to compair they are the same.
This returns a blank string whereas when I use the sections commented out in the first loop i get a really weired string back and when I use their simpleXor function it just returns complete nonsense.
There support is a bit useless as they "are not programmers"! So I am hoping someone can help me out who has used SagePay before.
Thanks in advance.
Managed to get it working:
Private Function base64Decode(ByVal strEncoded As String) As String
Dim output As String = ""
Dim bt64 As Byte() = System.Convert.FromBase64String(strEncoded)
For i As Integer = 0 To (bt64.Length - 1)
output &= System.Convert.ToChar(CInt(bt64(i))).ToString()
Next
Return output
End Function