Uruchamianie skryptów na innej stronie

0

Chciałbym napisać aplikację webową, która otwiera pewną stronę w nowym oknie (na nowej karcie) i aplikacja wysyła wywołania JavaScript, innymi słowy uruchamia funkcje JavaScript zdefiniowane na sterowanej stronie. Zakładam, że nie mam możliwości ingerencji w kod źródłowy, ani konfigurację serwera sterowanej strony. Nie wchodzi w grę specjalne konfigurowanie przeglądarki, aplikacja ma działać na każdym standardowym komputerze i na smartfonach.

Robiłem próby i jak uruchamiam inny plik HTML ze swojego dysku, to sterowanie działa prawidłowo. Natomiast, jak otworzę jakąś "obcą" stronę, która zawiera procedury, to próba uruchomienia czegokolwiek kończy się błędem. Nawet próba wywoałania zwykłego "alert" kończy się komunikatem "Permission denied to access property".

Próbowałem napisać aplikację desktopową w C# z osadzoną kontrolkę WebBrowser (oparta na IE, która jest na wyposażeniu) oraz GeckoFX (kontrolka oparta na silniku Gecko, którą trzeba doinstalować osobno). W obu przypadkach bez problemu uruchamiałem funkcje JavaScript dowolnej strony, którą otwierałem wewnątrz kontrolki, otrzymałem to, co chciałem.

W jaki sposób zrealizować to samo w przeglądarce, gdzie jest jeden plik HTML, który wywołuje okno poprzez "window.open" i zapamiętuje obiekt otwartego okna, a potem działa na tym obiekcie?

Do realizacji celu można wykorzystać wszystkie możliwości oferowane w HTML5 bez ograniczeń, tylko, jak to zrobić?

Strona docelowa pobiera i wyświetla dane na bieżąco w technologii AJAX i WebSocket. Próbowałem zapisać stronę i skrypty JavaScript tej strony, a w miejscach wywoływania danych w skrypcie podstawiałem oryginalny adres, ale wtedy był błąd CORS dotyczący pobierania z innej domeny. Jak to ominąć w skrypcie wywołującym?

0

Generalnie komunikacja pomiędzy domenami - czy to ajax, czy okna/iframe'y/obrazki itp - jest obarczona dodatkowymi obwarowaniami i bez specjalnych zabiegów nie da się jej uruchomić.

Komunikacja pomiędzy oknami działa w dwóch przypadkach: oba okna są z tej samej domeny (adresy hostów są identyczne, z tym samym protokołem i tym samym portem) albo poprzez wymianę eventów (window.postMessage - vide https://stackoverflow.com/questions/33640495/how-to-communicate-between-two-different-domains-through-javascript). W takim przypadku jedno okno nasłuchuje na dany komunikat, drugie okno mu taki komunikat (aka zdarzenie) wysyła (wraz z dołączonym obiektem z jakimiś danymi). Jeśli potrzebujesz komunikacji w dwie strony, to funkcja obsługi komunikatu może coś zwracać, możesz też zrobić nasłuch na komunikaty i ich wysyłanie w drugą stronę.

Jeśli chodzi o komunikację cross-domain, to albo dodaj do nagłówków http serwera nagłówki CORS, albo użyj JSONP (przy czym JSONP z JSON nie ma wiele wspólnego). Nie da się tego ominąć, bo gdyby się dało, to po co by było takie zabezpieczenie?

0
ŁF napisał(a):

Generalnie komunikacja pomiędzy domenami - czy to ajax, czy okna/iframe'y/obrazki itp - jest obarczona dodatkowymi obwarowaniami i bez specjalnych zabiegów nie da się jej uruchomić.

Komunikacja pomiędzy oknami działa w dwóch przypadkach: oba okna są z tej samej domeny (adresy hostów są identyczne, z tym samym protokołem i tym samym portem) albo poprzez wymianę eventów (window.postMessage - vide https://stackoverflow.com/questions/33640495/how-to-communicate-between-two-different-domains-through-javascript). W takim przypadku jedno okno nasłuchuje na dany komunikat, drugie okno mu taki komunikat (aka zdarzenie) wysyła (wraz z dołączonym obiektem z jakimiś danymi). Jeśli potrzebujesz komunikacji w dwie strony, to funkcja obsługi komunikatu może coś zwracać, możesz też zrobić nasłuch na komunikaty i ich wysyłanie w drugą stronę.

Jeśli chodzi o komunikację cross-domain, to albo dodaj do nagłówków http serwera nagłówki CORS, albo użyj JSONP (przy czym JSONP z JSON nie ma wiele wspólnego). Nie da się tego ominąć, bo gdyby się dało, to po co by było takie zabezpieczenie?

Dziękuję za odpowiedź, ale fundamentalnym założeniem jest brak możliwości ingerencji w stronę/aplikację sterowaną przy pełnej możliwości tworzenia aplikacji sterującej.

Mechanizm przesyłania komunikatów (postMessage) wydaje się być dobry, ale jeśli dobrze rozumiem, wymaga obsłużenia po obu stronach. Czyli do aplikacji sterowanej należałoby inna metodą wcisnąć krótki skrypt, który będzie zdolny odbierać i przetwarzać komunikaty. Nawet wystarczyłaby obsługa jednostronna, w kierunku komunikat od aplikacji sterującej (mojej) do sterowanej (zastanej).

Próbowałem odczytać element aplikacji sterowanej (za pomocą getElementById lub getElementByTagName) i z powodu tych samych ograniczeń też się nie dało.

Czy użycie JSONP obejdzie się bez ingerencji w aplikację sterowaną? Chodzi tylko o to, żeby do niej dopisać krótki skrypt, który będzie używany do odbierania komunikatów lub będzie wywoływać funkcje aplikacji.

Czy dodanie nagłówków CORS dotyczy aplikacji sterującej (możliwe do wykonania przy uruchomieniu na serwerze), czy aplikacji sterowanej (brak takiej możliwości, sprzeczne z założeniem).

Moje eksperymenty dowodzą, że CORS nie jest żadnym zabezpieczeniem, tylko uniemożliwia bezpośrednie sterowanie jednej aplikacji przez drugą w typowej przeglądarce, a sterowanie za pomocą GreaseMonkey lub aplikacji z osadzoną przeglądarką jest już możliwe.

Myślę, żeby "ugryźć" problem od innej strony:

Czy w PHP lub w ASP.NET da się zrobić następującą rzecz opisaną poniżej?
Aplikacja pobiera stronę z innej domeny, modyfikuję ją, a następnie wysyła ją do klienta (przeglądarki) w taki sposób, że oryginalne skrypty tej aplikacji będą działać bez zmian, czyli dla nich będzie zachowana zgodność domeny aplikacji. Coś a'la GreaseMonkey, ale na serwerze, a klient dostaje stronę w oryginalnej domenie, ale ze zmodyfikowaną treścią. Może w nagłówkach HTTP wystarczy coś pozmieniać? Zwykłe odczytanie i wysłanie treści nie wiele da, bo wtedy strona będzie nie w oryginalnej, tylko w mojej domenie.

Jeżeli w aplikacji HTML jest link bezwzględny do pliku JS na innej domenie, a JS wywołuje zdarzenie AJAX, to czy decyduje domena pliku HTML, czy pliku JS?

Jeżeli w żaden sposób nie da się usunąć przeszkód spowodowanych przez CORS, to w jaki sposób można wyłączyć respektowanie CORS w IE, Firefox, Chrome i na smartfonach? Teoretycznie, to mogłaby istnieć przeglądarka, która nie sprawdza, czy domeny są te same i zawsze pozwala wpłynąć na jedną aplikację z drugiej.

0

Jeśli nie masz możliwości zrobienia zmian w aplikacji, z którą chcesz się komunikować, to pozostaje tylko zrobienie czegoś w rodzaju proxy, czyli to co miałeś na myśli pisząc "aplikacja pobiera stronę z innej domeny, modyfikuję ją, a następnie wysyła ją do klienta".

CORS nie ominiesz, bo istotą działania CORS jest właśnie umożliwienie komunikacji cross-domain. Bez CORS taka komunikacja jest niemożliwa (za wyjątkiem JSONP) w żadnej popularnej przeglądarce.

0

Przejdę do konkretów. Chciałbym na własne potrzeby zrobić aplikację "spinającą" internetowe odbiorniki radiowe http://websdr.org/ i zwiększającą wygodę korzystania z nich.

Chodzi o to, że odbiornikiem steruję z interfejsu aplikacji. Dalszy rozwój, czyli baza odbiorników, możliwości i sposób sterowania, to już inny temat.

Robię próby z aplikacją desktopową w C# typu Windows Forms. Przeglądarka WebBrowser nie nadaje się, bo Internet Explorer nie obsługuje WebAudio. Zainstalowałem bibliotekę GeckoFX i XulRunner. Aplikacja działa tak, że tworzę obiekt przeglądarki klasy GeckoFX, kontrolka przeglądarki nie jest widoczna w interfejsie, do niej wczytuję stronę wybranego odbiornika, a potem poprzez wywoływanie skryptów steruję częstotliwością i modulacją. Dźwięk odbieranej stacji słyszę bezpośrednio z przeglądarki, poprzez interfejs WebAudio (dlatego IE i tym samym WebBrowser w obecnej wersji nie nadaje się do tego celu). Porobiłem próby i działa to doskonale, dokładnie tak, jak chciałem. Oczywiście odbiorniki nie są moją własnością, stąd założenie niemodyfikowania aplikacji sterowanej, ale oczywiście dopuszczam modyfikowanie struktury DOM po stronie klienta po wczytaniu odbiornika.

Dlatego myślę o takiej samej aplikacji, ale webowej, która pozwala korzystać z odbiorników na smartfonie i innych komputerach, z tego, co mi się wydaje, w IT powoli odchodzi się od aplikacji desktopowych na rzecz webowych. Robiłem takie próby, że mam plik HTML, w którym jest jeden przycisk, który otwiera nowe okno z drugim plikiem i na tym drugim oknie wywołałem alert i jakąś funkcję JS i zadziałało. Potem otworzyłem stronę odbiornika i już nie zadziałało z powodu różnych domen. Robiłem też próby polegające na zapisaniu strony odbiornika i dołączonych do niej JSów (bez zdjęć i elementów niezwiązanych z odbiornikiem), nie udało mi się uruchomić, bo w miejscu, w którym miał pobrać się strumień danych (właściwie w kilku, adres względny zmieniłem na adres bezwzględny) był zgłaszany błąd bezpieczeństwa (różnica domen). Wygląda na to, że w ten sposób się po prostu nie da bez zmian w aplikacji sterowanej (czyli w tym wypadku odbiornika internetowego).

W takim razie zapytam inaczej, bo nie mam żadnego doświadczenia w tworzeniu aplikacji na Androida, nigdy tego nie robiłem. Czy w aplikacji na Androidzie jest możliwe albo uruchomienie ukrytej przeglądarki, albo osadzenie obiektu przeglądarki internetowej (niekoniecznie widocznej w interfejsie) podobnie, jak obiekt "WebBrowser" w aplikacjach desktopowych tak, żeby sterować aplikacją poprzez modyfikację DOM i wywoływanie funkcji JavaScript dokładnie tak, jak bez żadnego problemu można zrobić na komputerze? Czy do tego nadaje się technologia Java, czy C# w bibliotece Xamarin, czy Cordova?

1 użytkowników online, w tym zalogowanych: 0, gości: 1