HypRetrieve not retrieving correct status code - excel

Background
I have two databases that I need to connect to. One is in Hyperion and the other one is in ESS. I have imported the smartview.bas as stated by the documentation and I am attempting to use the functions within it. I have dummy sheets (SavedLogHyperion and SavedLogESS) for each enviroment to make sure the users logs in before running all the code. I want to retrieve the proper error code if the user closes the window without logging or other things that may prevent the successful login.
Problem
The HypRetrieve only acknowledge for the first result: if the user was able to log to Hyperion environment, but if ESS login window is cancelled or provided with non-valid credentials and then closed, it detects the code as 0 ("Ok"), thus detecting a successful login for the second environment when it was not.
Code
I wrote a function to retrieve the number, I thought that it could be a time thing and that is why I made it (so for the main code could resolve on time), but it seems like it is not.
Function Return_NumCodeSVHypRetrieve(VarTxtSheetToLogin As Variant) As Long
Dim NumCodeHypRetrieve As Long
NumCodeHypRetrieve = HypRetrieve(VarTxtSheetToLogin)
Return_NumCodeSVHypRetrieve = NumCodeHypRetrieve
End Function
This function is called in my main sub
Sub Main()
Dim NumCodeConnectionSheet1 As Long
Dim NumCodeConnectionSheet2 As Long
NumCodeConnectionSheet1 = Return_NumCodeSVHypRetrieve("SavedLogHyperion")
NumCodeConnectionSheet2 = Return_NumCodeSVHypRetrieve("SavedLogESS") 'If I log in "SavedLogHyperion", this variable becomes 0 too, or any other error code that variable had
End Sub
Question
How can I make the correct code according to the sheet attempted to log be correctly saved? I am clueless on what may be the approach

Solution:
The problem seems to be on how the function works; I noticed that when the function is applied, it activates the sheet, which lead me to believe that there was a problem on timing events, I came with the following solution, which has been basically to provide the scenario that I saw the function is expecting to, also I noticed that if I set the NumCode to retrieve as long as the direct result, it does not behave as expected, my approach was to declare it a variant and then cast it to a long instead.
Function Return_NumCodeSVHypRetrieve(VarTxtSheetToLogin As Variant) As Long
Dim VarNumCode As Variant
'It seems the function relies on the sheet being activated and if the Retrives does it, it takes miliseconds to do, which are not sync with excel life cycle, thus causing missreadings
Sheets(VarTxtSheetToLogin).Visible = True: Sheets(VarTxtSheetToLogin).Select: DoEvents
VarNumCode = HypRetrieve(VarTxtSheetToLogin)
Sheets(VarTxtSheetToLogin).Visible = False
Return_NumCodeSVHypRetrieve = CLng(VarNumCode)
End Function

Related

Reset VBA variable when code starts / stops

Building an automated logging process where the log calls are automatically inserted into any applications VBA code. For example, log the name of each sub or function when it is called. If sub SUB_A calls function FUNCTION_Q then the log file will read:
SUB_A
FUNCTION_Q
I need to add in log points to seperate processes so that I can see the start and end. An example output could be:
New Process started
SUB_A
FUNCTION_Q
New Process started
SUB_C
FUNCTION_D
FUNCTION_T
Issue is how to determine the start / end of a process. The Excel application may have multiple processes triggered by the user without closing Excel to reset anything. I'd thought of declaring a boolean variable (which initialises as False) that gets set to True if it is False but the value of True persists after the code has ended.
Any ideas?

How to Know an Alert Pop-Up Has Occurred

I am automating a website. I am using SeleniumBasic in Excel VBA.
I have a simple Pop-Up, or Alert, with an OK button.
I cannot access the Pop_Up by using Inspect so I have no HTML to show.
When the Pop-Up occurs, I respond with Driver.SwitchToAlert.Accept. It goes away, as desired.
I don't know how to check programmatically if the Pop-Up is present.
If I assume that the Pop-Up may have occurred and use this code on a just-in-case basis, i.e. use the code without the Pop-Up existing, the program stops without any error message.
Is there a way to check if the Pop-Up window exists before I respond?
Well, I found the answer:
I got this code from someone who got it from someone else.
Private Function AlertIsPresent() As Boolean
'Returns true if an alert is present, false otherwise
Dim T As String
On Error Resume Next
T = Driver.Title 'This raises error 26 if an alert(pop-up) is displayed
AlertIsPresent = (26 = Err.Number)
End Function
If function returns 'true', use the Driver.SwitchToAlert.Accept to close it.

How can i post data using this code below and also tell user to wait while sending message

Iam currently using b4a for android
here is the error which comes
enter code here
',' expected.`enter code here`
enter code here
Dim j As HttpJob
j.Initialize("", Me)
j.PostString($"http://kccug.com/KabojjaApp/RecieveSMS.ashx?customerId=${act}&s=${edtMessage.Text}&d=${getdate(DateTime.Now)}&id=${NewID}&ph=${phone}&f=${sx}"$ )
Wait For (j) JobDone(j As HttpJob)
If j.Success Then
Log(j.GetString)
End If
enter code here
You are using j.PostString which sends a post request. However, you are not using it correctly. j.PostString requires a second parameter: the post data. B4A expects you to put in a comma and the second paramter after the url, but you are only giving 1 parameter (the url) to the function. However, looking at your URL, it seems like your backend is handling stuff through GET requests only anyway, not POST. So really, what you should be using is j.Download. Try this code:
Dim j As HttpJob
j.Initialize("", Me)
j.Download($"http://kccug.com/KabojjaApp/RecieveSMS.ashx?customerId=${act}&s=${edtMessage.Text}&d=${getdate(DateTime.Now)}&id=${NewID}&ph=${phone}&f=${sx}"$)
Wait For (j) JobDone(j As HttpJob)
If j.Success Then
Log(j.GetString)
End If
It's exactly the same, but it uses Download instead of PostString.

Excel Application.Ready=False When Receiving Data via COM dll

I am delivering external data using the dispatch interface via a COM dll to an Excel plugin. In the VBA sink method, I check that Application.Ready = True before trying to write the data to the appropriate cell like this,
If Application.Ready = True Then
With Workbooks(bookName).Sheets(sheetName).Range(rangeName)
.Value = thisData
End With
Else
Debug.Print "Dropped Payload"
End If
I don't want to just drop the data, so I've tried to do a few things to get it right.
Call Application.OnTime instead of setting the value. Unfortunately, Excel would not let me call Application.OnTime when Application.Ready=False.
Use the technique here to start a Windows timer that then calls OnTime. The problem here was that multiple events were coming in on top of each other and they were all trying to access the AfterUDFRoutine1 simultaneously, causing a crash.
So my latest thought is to put the data into a queue and then drain the queue when Application.Ready=True. To implement this, I need an event to fire when Application.Ready changes state, but I can't find the event in the list. Does anybody know if this exists and how to expose it? Alternatively, if somebody has a better idea of how to make this work I'm very open to it. The only suggestion I can't do is to use RTD instead of the dispatch I have already - I can't change that part.

How can I execute a long running process in VBA without making pc crawl?

I have a VBA application that creates an instance of a COM object and then continuously polls the objects DataReady property to see if there is new data. When new data is available it sticks the data into a spread sheet. The problem is this macro (vba sub routine) continually runs and this slows down excel to a crawl and makes the computer somewhat unusable while the process is running. Is there a way that I can start this process on a separate thread or do something like a .NET background worker?
My two attempts were to use a while loop like this..
While(True)
If(myObject.DataReady)
Do some stuff here
End If
WEnd
and then this
Sub GrabNewPoint()
If (myModule.NewDataReady_Receiver = True) Then
Do some stuff here...
End If
If (StopTest = False) Then
NextTime = Now() + TimeValue("00:00:20")
Application.OnTime NextTime, "GrabNewPoint"
End If
The second attempt definitly works better but it still slows things down considerably. Is there a better solution?
My COM object is a class library that I wrote in C#. I can add events that fire in the Class Library when data is ready but how do I listen for those events in the VBA program?
Have you tried using DoEvents?
While(True)
If(myObject.DataReady)
'your code here
End If
DoEvents
WEnd
I would think the best solution is to have the COM object raise a VBA event whenever data is ready.
If that is not an option (no control over COM object, etc.) then you will HAVE to spin the CPU. All you can do is increase the time interval between checking the DataReady property, which you already discovered in your second option. I would figure out just how fat you can increase the interval without losing functionality and leave it there.
Try this, see if things improve.
Just pause, let the CPU fly... key is to trap it here so it releases as long as you like
Public Sub App_Hard_Wait_DoEvents(dblSeconds As Double)
If dblSeconds = 0 Then Exit Sub
Dim varStart As Variant
varStart = Timer
Do While Timer < (varStart + dblSeconds)
DoEvents
Loop
End Sub
DO
Call App_Hard_Wair_DoEvents(10)
loop until (myObject.DataReady)

Resources