백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.문제
사용자 인터페이스가 정지되지 않도록 백그라운드에서 쿼리를 실행하거나 동시에 여러 쿼리를 실행한 다음 결과를 결합하려고 합니다. 때로는 백그라운드 쿼리의 '실행 완료 시' 스크립트에 필요한 모든 기능을 넣는 것이 어렵습니다.
해결책
각 쿼리는 모든 스크립트(쿼리 및 원본 스크립트)가 액세스할 수 있는 새 네임스페이스에 결과를 저장합니다.원본 스크립트는 계속 진행하기 전에 결과를 계속 확인합니다.
//Example script which runs queries in the background and references their results
//once finished.
Names default to here(1);
// Namespace to share data between background query and this script
ns = new namespace( "queries" );
// Flags which the background query will set to 1 when the background query is complete
ns:query1isdone = 0;
ns:query2isdone = 0;
// Open a window to display results
win = New window("Query Status", show menu(0), show toolbars(0),
text box("Status of queries:"),
tb = tablebox( string col box( "Query" , { "Query 1", "Query 2" } ),
string col box( "Status", { "Not Started", "Not Started" } ) ),
tbStatus = text box("Starting queries.")
);
wait(0); //make sure window shows up
// Define and start background queries
// First Query
sql_query1 = New SQL Query(
Connection( "ODBC:DSN=Test Source;DATABASE=Test Database;" ),
QueryName( "Query" ),
Select( vars ),
From( table ),
Where( condition )
);
sql_query1 << Run Background( OnRunComplete(
Names default to here(1);<BR /> ns = namespace( "queries" );
ns:dt1 = queryResult;
ns:query1isdone = 1;
) );
// Second Query
sql_query2 = New SQL Query(
Connection( "ODBC:DSN=Test Source;DATABASE=Test Database;" ),
QueryName( "Query" ),
Select( vars ),
From( table ),
Where( condition )
);
sql_query2 << Run Background( OnRunComplete(
Names default to here(1);<BR /> ns = namespace( "queries" );
ns:dt2 = queryResult;
ns:query2isdone = 1;
) );
// Every second check if the query is done (timeout after 10 seconds)
i=0;
allqueriesdone = 0;
starttime = tick seconds();
while( ( i < 10 ) & allqueriesdone == 0 ,
i++;
wait(1);
if( ns:query1isdone == 1,
tb << delete row( 1 );
tb << insert row( 1, {"Query 1", "Complete"} );,
tb << delete row( 1 );
tb << insert row( 1, {"Query 1", "Still Running"} );
);
if( ns:query2isdone == 1,
tb << delete row( 2 );
tb << insert row( 2, {"Query 2", "Complete"} );,
tb << delete row( 2 );
tb << insert row( 2, {"Query 2", "Still Running"} );
);
if( (ns:query1isdone == 1 ) & (ns:query2isdone == 1 ), allqueriesdone = 1 ); //indicate that everything finished
tbStatus << Set Text( "Queries are running, " || format(tick seconds() - starttime, "Fixed Dec", 12, 1) || " seconds elapsed." );
win << bring window to front;
);
// Show an error if any queries didn't finish
if( allqueriesdone == 0,
tbStatus << Set Text("Error, a query didn't finish and is still running!"),
tbStatus << Set Text("Queries finished after " || format(tick seconds() - starttime, "Fixed Dec", 12, 1) || " seconds.");
//win << Close Window; //could close window here
);
// Now reference the data tables
show( ns:dt1 );
show( ns:dt2 );백그라운드에서 쿼리를 실행하고 싶지만 결과와 상호 작용해야 합니다.이 방법을 사용하면 결과와 상호 작용하기 전에 여러 백그라운드 쿼리를 완료할 수 있습니다.
유용Re: 백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.안녕하세요 @마크데이튼 ,
제가 방금 수정한 스크립트의 부족한 점을 지적해 주셔서 감사합니다. OnRunComplete 스크립트에는 이름 기본값이 here(1)로 설정되어 있지 않았기 때문에 계획한 대로 정확히 작동하지 않았습니다.업데이트 전후의 네임스페이스에 대한 설명은 다음과 같습니다. 단지 만들어진:
개요
네임스페이스 'queries'가 어떻게 사용되는지 참고하세요. 만들어진 상위 스크립트에서 참조됨 OnRunComplete 스크립트에서.ns 변수 자체는 'queries' 네임스페이스를 참조하는 데에만 사용됩니다.예를 들어, 새 스크립트 창 창에서 다음을 실행할 수 있습니다.
Names default to here(1);
ns = New Namespace("queries");
ns:a = 1
두 번째 스크립트 창은 다음을 호출하여 a 값을 얻을 수 있습니다.
Names default to here(1);
Show(Namespace("queries"):a);
하지만 다른 창에서는 쉽게 ns에 액세스할 수 없습니다. 그러나 다른 창에서 새 변수를 정의한 다음 비슷한 방식으로 액세스할 수 있습니다.
Names default to here(1);
nsreference = Namespace("queries");
Show(nsreference);
또는 코드를 더 쉽게 읽을 수 있도록 두 창에서 동일한 변수 이름을 사용할 수 있습니다.변수 자체는 서로 다른 네임스페이스에 정의되어 있으므로 다르지만 동일한 것을 참조하므로 동일한 방식으로 사용할 수 있습니다.
Names default to here(1);
ns = Namespace("queries");
Show(ns:a);
위의 예제 스크립트에서 변수가 사용되는 방식은 다음과 같습니다. 'queries'라는 네임스페이스를 참조하는 각 here 네임스페이스에 'ns'라는 변수가 생성되어 해당 스크립트 간에 값을 더 쉽게 공유할 수 있습니다.
변경 전 - 이름 기본값을 여기(1)로 설정하여 각 OnRunComplete 스크립트를 시작하지 않고 이것이 어떻게 작동하는지:
더보기...
변경 후 - 현재 스크립트가 어떻게 작동하는지
스크립트에서는 4개의 네임스페이스를 사용합니다.
- 상위 스크립트 창의 here 네임스페이스
- 첫 번째 쿼리의 OnRunComplete 스크립트에 대한 here 네임스페이스
- 두 번째 쿼리의 OnRunComplete 스크립트에 대한 here 네임스페이스
- 상위 스크립트와 두 개의 OnRunComplete 스크립트에서 참조하는 'queries'라는 네임스페이스
상위 스크립트의 ns 변수는 here 네임스페이스에 정의되어 있습니다. 참조 New Namespace()로 생성된 쿼리 네임스페이스입니다.즉, 스크립트 창만 ns에 액세스할 수 있지만 해당 JMP 인스턴스의 다른 모든 항목은 ns가 참조하는 쿼리 네임스페이스 내에 저장된 모든 항목을 참조할 수 있습니다.
OnRunComplete 스크립트는 새 환경에서 열리며 상위 스크립트의 여기 네임스페이스에 액세스할 수 없습니다.따라서 ns라고도 불리는 새 변수가 해당 스크립트의 여기 네임스페이스에 정의되고 Namespace()를 사용하여 'queries' 네임스페이스를 참조하도록 설정됩니다.각 실행 완료 스크립트는 자체 here 네임스페이스에 ns라는 자체 변수를 생성하지만 각 변수는 동일한 '쿼리' 네임스페이스를 참조하도록 설정됩니다.
Re: 백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.먼저, 이 스크립트를 제공해 주셔서 감사합니다. 네임스페이스 사용, SQL 쿼리 스크립팅, 완료 여부 테스트 상태 피드백 제공, 결과 관리 이 스크립트는 JSL의 몇 줄에 많은 내용을 담고 있습니다.대부분 따라갈 수 있지만 저는 네임스페이스를 정의하고 사용한 경험이 많지 않아서 질문이 있습니다.
스크립트의 두 번째 줄에서는 ns ~이다 ~로써 정의 된 :
ns = new namespace( "queries" );
그러면 그럴 것 같다 ns Run Background() 문에서 다시 정의됩니다.
sql_query2 << Run Background( OnRunComplete(
ns = namespace( "queries" );
ns:dt2 = queryResult;
ns:query2isdone = 1;
) );
sql_query1 & 2 내의 네임스페이스는 스크립트 시작 부분에 정의된 것과 동일한 네임스페이스입니까? 그래야 할 것 같습니다. 아니면 쿼리 문에 로컬인 네임스페이스입니다. 이름의 기본값은 여기에 있습니다(1) 처음에 진술? 왜? ns Run Background() 문 내에서 정의해야 합니까?
간단하고 명확하며 아름다운 코드에 다시 한번 감사드립니다.
Re: 백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.그래도 빡빡한 부분에서 참조할 수 있는 좋은 코드입니다. 
Re: 백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.안녕 @바이런_JMP ,
대화형으로 실행되는 쿼리의 상태를 확인하는 것이 목표라면 사용자는 쿼리 빌더만 살펴봐야 한다는 데 동의합니다.이 상태 창은 완료된 후 스크립트에서 결과를 참조하는 것과 같이 사용자가 간단한 웹 검색으로 찾는 데 어려움을 겪는 쿼리 작업 부분을 보여 주기 위한 것입니다. 솔직히 말해서 최소한의 예를 떠올리는데 어려움을 겪었던 기억이 납니다.더 나은 사용 사례가 있다고 확신합니다 ...
Re: 백그라운드에서 쿼리를 실행하고 완료될 때까지 기다린 후 나머지 JSL 스크립트에서 참조합니다.정말 흥미로운 프로젝트 아이디어인 것 같습니다.
쿼리 빌더에는 실행 중인 쿼리 수와 진행 상황을 확인할 수 있는 진행률 탭이 있다는 점을 알고 싶었습니다. 어쩌면 이것이 정보를 처음부터 가져오려고 하기보다는 쿼리 빌더 플랫폼을 스크립팅하여 이 정보를 표시하는 방법이 될 수 있을까요?