ᲖᲐᲠᲘ

არიან ისეთებიც, ვინც ამ ამბებს შენამდე კითხულობს.
გამოიწერეთ უახლესი სტატიების მისაღებად.
ელფოსტა
სახელი
გვარი
როგორ გინდა წაიკითხო ზარი
არ არის სპამი

კითხვა: გარე Native Api კომპონენტი C++-ში Linux-ისთვის (Ubuntu x64) 1С 8.3-ზე


VK-ს ვწერ, უბუნტუზე 1-ს ვერ ვუკავშირდები. 1-დან ეგზაპლიც კი არ არის დაკავშირებული. ასე რომ, კითხვა ამის შესახებ:

1) ვცდილობ დავაკავშირო VK სტატიაში მოცემული VNCOMPS მაგალითიდან

(ბმული შეგიძლიათ იხილოთ ბოლოში: "კოპირება").
შინაგანად, NativeApi პროექტს აქვს მაკიაჟი. მასთან ერთად ვაშენებ .so ბიბლიოთეკას Ununtu-ზე.
მაგრამ "დააკავშირე გარე კომპონენტი" 1 აფრინდება.
ანალოგიურად, თუ ვაშენებ "build.sh"-ის გამოყენებით (პროექტის ძირში).

თავად მაკიაფილში ვცვლი დროშას m32-დან m64-ზე იმიტომ 1c და თავად x64 სისტემა. (m32 პარამეტრით მაინც არ აიღებს)
აქ მოცემულია VK-ის დარეკვის მაგალითი 1C 8.3-დან:
კავშირი დასრულებულია = შეაერთეთ გარე კომპონენტი("/home/alexeyubuntux64-20 gb/Documents/VNCOMP83/example/NativeAPI/AddInNative.so", "AddInNative", ExternalComponentType.Native); არის სტატია მხოლოდ ამ თემაზე.
მაგრამ, რამდენადაც მე ვხედავ, ყველა ეს პუნქტი უკვე გათვალისწინებული და გასწორებულია VNCOMPS-ის მაგალითში.

მაგრამ, ფაქტობრივად, ბიზნესი შედგენის პარამეტრებში. MB 32 ბიტიანი გარე კომპონენტი ჩვეულებრივ იკავებს 32 ბიტიან 1c-ს, მაგრამ მე განვათავსე Ubuntu x64 1c enterprise83 8.3.5-1486 amd64. და მე მსურს მისთვის VK აიღო.

ვინმეს ხომ არ გაქვთ იდეა როგორ მოვაგვარო ეს საკითხი?
VNCOMPS-ის მაგალითი უნდა იმუშაოს, მაგრამ build-ის პარამეტრების კორექტირებაა საჭირო, ან თავად პლატფორმა, რომელზეც მე ვამოწმებ, არასწორია.

პასუხი:საინტერესოა, შესაძლებელია თუ არა Java-ში გარე კომპონენტის დაწერა?

შეკითხვა: გარე კომპონენტი (მშობლიური) არ არის დაკავშირებული


შედგენილი მაგალითი ITS-ით, 64 და 32 ბიტიანი სისტემებისთვის.

ვაკავშირებ ასე:
ConnectionResult = ConnectExternalComponent (CDLLPath, "Comp", ExternalComponentType.Native); ერთი კომპიუტერი აკავშირებს, მეორე არა. OS-ში არის განსხვავება. სადაც კავშირი მიდის, არის Win7, სადაც არ არის Win10. ამავდროულად, სტანდარტული კომპონენტები მუშაობს კომპიუტერზე, სადაც ჩემი კომპონენტი არ მუშაობს.

ტესტირებულია სხვადასხვა პლატფორმებზე (8.3.4.482, 8.3.6.2100, 8.3.11.2700, 8.3.12.1412).

როგორ გავიგოთ, რატომ არ უკავშირდება?

პასუხი: vc_redist არ დაგავიწყდა?

კითხვა: 1C8 და გარე კომპონენტი Native ტიპის


Შუადღემშვიდობის.
არსებობს BP 3.0.50.12-ის კონფიგურაცია და აწონვის განხორციელების სურვილი კომპანია Scales-Soft-ისგან UniServerAuto-ს გამოყენებით.
დეველოპერებმა შეადგინეს Native კომპონენტი Windows 32 და 64-ისთვის და ჩასვეს არქივში მთავარი ფაილით. ასევე არსებობს მაგალითი 1C-სთვის, როგორ შეიძლება გამოითვალოს წონა. მასში, ბინარული მონაცემებით განლაგების დახმარებით, მითითებულია ეს არქივი, როგორც მე მესმის. მაგალითში ყველაფერი კარგადაა: კომპონენტი დამონტაჟებულია, დაკავშირებულია, შემდეგ კავშირი დამყარებულია და წონა იკითხება.
მაგრამ როგორც კი დაიწყებთ გადატანას 1C-ზე, წონა არ იკითხება. როგორც ჩანს, ყველაფერი უბრალოდ დაწერილია, მაგრამ არ მესმის სად არის საკომისიო.
ვის ექნება ცოტა დრო - დაეხმარეთ, ერთი თვალით შეხედეთ, იქნებ გამოსავალი ზედაპირზეა, მაგრამ სადღაც არასწორ ადგილას დავდივარ და რაღაცას ვაკეთებ. აქამდე არასდროს მიმუშავია მშობლიურ ტექნოლოგიაზე...

და დანართში არის ჩემი დამუშავების ტექსტი

პასუხი:

აჰა, ახალი ამბავი მაქვს...
მე ახლახან დავიწყე ეტაპობრივად ყურება, რა მომენტში იწყება ის ჩავარდნას. ამისთვის შევქმენი ცარიელი მონაცემთა ბაზა და დამუშავება ბრძანებით. მიმწოდებლის მაგალითის ანალოგიით, მე გადავეცი განლაგება ახალ კონფში - ის მუშაობს მეორედ. იმათ. პირველად არა, მეორედ კი. ამან გამოიწვია იდეა, რომ მისი დამუშავებისას მაინც საჭირო იქნებოდა კომპონენტისა და ობიექტის კავშირის გამიჯვნა სხვადასხვა პროცედურების მიხედვით.
შემდეგ გადავეცი ჩემს მონაცემთა ბაზაში განლაგების კავშირით - მუშაობს. ფუჰ, ეს უკვე კარგია .... მაგრამ მე მინდა კონფიგურაციაში ცვლილებების შეტანის გარეშე, ასე რომ გადავიდეთ

ვცდილობ დავამატო განლაგება დამუშავებას. მისი ზომა მაშინვე იზრდება 10 კბ-დან 3 მბ-მდე და შეინიშნება მნიშვნელოვანი შენელება - არ ჯდება. ვიწყებ თხრას dll-ის საშუალებით კომპონენტის შეერთებისკენ. იმათ. ძირითადად იგივეა, რაც თქვენ დაიწყეთ. მაგრამ არის ერთი "მაგრამ": მომხმარებლის საქაღალდეში dll-ის სახელის მოძიებით, შევამჩნიე, რომ ეს dll დევს იქ, სადაც (როგორც მე მესმის) ემატება 1C-ში რეგისტრირებული dll-ები:
C:\Users\USER\AppData\Roaming\1C\1cv8\ExtCompT
შესაბამისად, არ არის საჭირო dll-ის სრული გზის გამოყენება, შეგიძლიათ უბრალოდ დაწეროთ მისი სახელი:
ConnectExternalComponent ("Add1CUniServerAuto32.dll", "UniServerAuto", ExternalComponentType.Native);

ვცდილობ ... რეგისტრაციას იფიცებ, მაგრამ აწონვის შედეგს აბრუნებს. გამოდის, რომ dll უკვე რეგისტრირებულია, რაც ნიშნავს, რომ თქვენ უბრალოდ უნდა დააკავშიროთ იგი. ვხსნი და ყველაფერი მუშაობს.
ვაჯამებ:
1. აწონვის დამუშავებისას პროცედურა გახსნისას დავამატე გარე კომპონენტის შეერთება და ობიექტთან შეერთება.
2. dll-ის გზა მე არ დავწერე, უბრალოდ მივუთითე მისი სახელი.

ახლა ვჯდები და ვფიქრობ, როდის დაინსტალირდა dll 1C-ში? პროგრამული უზრუნველყოფის ინსტალაციის დროს? ძნელად... ამ dll-ის დეველოპერის კონფიგურაციის გაშვების დროს სად არის დაყენებული ფორმის გახსნისას? არ ვიცი, მაგრამ ახლოს მეჩვენება... რას ფიქრობ?
და მეორეც, ახალ ადგილას, როცა არის იგივე ტერმინალის დაყენების აუცილებლობა, რა უნდა გაკეთდეს იმისათვის, რომ ყველაფერი იმუშაოს? დააინსტალირეთ პროგრამა მთლიანად, გაუშვით მიმწოდებლის კონფიგურაცია სამუშაოს შესამოწმებლად და შემდეგ (თეორიულად) ჩემი დამუშავება უნდა იმუშაოს? რაღაც ცოტა რთულია... ან პროგრამული უზრუნველყოფის დაინსტალირების შემდეგ ჩემს დამუშავებაში ერთხელ გავაკეთო InstallExternalComponent?

სიამოვნებით მოვისმენდი თქვენს აზრს ამ თემაზე...

შეკითხვა: გარე კომპონენტი.dll


კარგი დღე ყველას.
Კითხვა.
dll კომპონენტი, რომელიც კარგად მუშაობს 1C 7.7-ში
1s 8.1-ში საერთოდ არ მინდა ჩატვირთვა...
სცადე და ჩასვით C:\Program Files\1cv81\bin\cache1c.dll-ში
ვცადე რეგისტრაცია regsvr32 "C:\Program Files\1cv81\bin\cache1c.dll" გამოყენებით
დარეგისტრირდა უპრობლემოდ.
როდესაც ვცდილობ მასზე წვდომას, მე მივიღებ შეცდომის შეტყობინებას:

შეცდომა გარე კომპონენტის ჩატვირთვისას! cache1c.dll
პროცედურის შესრულების ღილაკი დაწკაპუნეთ(ღილაკი) გარე კომპონენტის ჩატვირთვის მცდელობა( "C:\Program Files\1cv81\bin\cache1c.dll"); გამონაკლისის ანგარიში ( "შეცდომა გარე კომპონენტის ჩატვირთვისას!"+ "cache1c.dll"); მცდელობის დასასრული; მცდელობა // მიიღეთ კომპონენტის ობიექტი. // m = ახალი ("cache1c.GTMcmd" ); m = New COMObject("cache1c.GTMcmd" ); გამონაკლისის ანგარიში(); მცდელობის დასასრული; დასრულების პროცედურა

პასუხი:შეუძლებლობამდე ბანალური...
აუცილებელია ზარებს შორის პაუზების შენარჩუნება (მილიწამებში)...
Procedure ButtonExecuteClick(Button) მცდელობა // მიიღეთ კომპონენტის ობიექტი. m = New COMObject("cache1c.GTMcmd" ); გამონაკლისის ანგარიში ( "გარე კომპონენტის ობიექტის შექმნა ვერ მოხერხდა"); მცდელობის დასასრული; m.RemoteHost = "192.168.1.101" ; m.RemotePort = 6330; m.Connect(); მ.პაუზა(100); ...... და ა.შ
1s 7.7-ისთვის - ეს არ არის საჭირო, გამოდის, რომ ტირაჟი უფრო სწრაფია.

კითხვა: გარე კომპონენტის მუშაობა 1C სერვერთან ...


Შუადღემშვიდობის,

არის C ++-ში დაწერილი გარე კომპონენტი, რომლის ამოცანაა ინფორმაციის მიღება გარე მონაცემთა ბაზიდან და მოთხოვნის შედეგის დაბრუნება 1C-ში მნიშვნელობების ცხრილის სახით.
მიმდინარე მომენტში მნიშვნელობების ცხრილის შესაქმნელად გამოიყენება IDispatch* pBackConnection ინტერფეისი, რომელიც მიიღება პარამეტრად Init() ფუნქციაში. გარდა ამისა, მე უბრალოდ, 1C ფუნქციების გამოყენებით, ვაყალიბებ მნიშვნელობების ცხრილს, ვავსებ და ვაბრუნებ მეორე პარამეტრს CallAsFunc-ში (...).
პრობლემები დაიწყო 1C თინ კლიენტებზე გადასვლით. სერვერის მხრიდან, გარე კომპონენტი ნამდვილად არ იწყება. თქვენ შეგიძლიათ გაუშვათ ის კლიენტის მხარეს, მაგრამ ეს ყველაფერი ყავარჯნებს ჰგავს და 1C-ში ცდება ზოგადი "კლიენტ-სერვერის" ლოგიკიდან. მაგალითად, კლიენტს არ ესმის რა არის მნიშვნელობების ცხრილი, პრობლემები "გლობალურ" ცვლადებთან, სესიებთან და ა.შ.
NativeAPI ამ მხრივ კიდევ უფრო შემცირებულია.
ტამბურინთან ცეკვამ განაპირობა ის, რომ მე შევძელი გარე კომპონენტის გაშვება 1C სერვერის ქვეშ, მაგრამ მუშაობა ხდება მანამ, სანამ არ მოხდება PBackConnection-ზე Invoke-ის გამოძახების მცდელობა. სერვერის 8.2 64-ბიტიანი ვერსია ცდილობს რაღაცის გაკეთებას მანამ, სანამ არ ამოიწურება, ხოლო 32-ბიტიანი ვერსია (VK, ბუნებრივია, ასევე 32-ბიტიანია) მაშინვე იშლება.
მე ვვარაუდობ, რომ 1C სერვერი არ ემსახურება მუშაობის ამ რეჟიმს.
შესაბამისად, ჩნდება კითხვები, ეს დროებითია თუ 1C-ის ლოგიკა მცირდება ამ სქემის გაუქმებამდე? თუ შეუძლებელია ამ გზით შიდა 1C სტრუქტურების (ფასეულობების ცხრილის) შექმნა, არის თუ არა, პრინციპში, აღწერა, თუ რა არის მნიშვნელობების ცხრილი სისტემის დონეზე, რათა შევეცადოთ მისი შექმნა C +-ში. +, შეავსეთ იგი და შემდეგ უბრალოდ გადაიტანეთ 1C, როგორც დაბრუნების პარამეტრი? ვისურვებდი მაინც მივიღო მიმართულება, თუ რა მიმართულებით უნდა ამოთხარო.

Გმადლობთ.

პასუხი:

შენ ერთს წერ და მეორეს გულისხმობ.
1C გარემოში, ცვლადების გამოცხადება, რომლებიც ხილული იქნება სხვადასხვა სესიებზე, ახლა შეუძლებელი არ არის და ადრეც შეუძლებელი იყო. განსხვავებული სესია ფიზიკურად განსხვავებული პროცესია.
Session არის მონაცემთა ბაზის კავშირის სესია, ე.ი. მომხმარებლის სესია. ან რამე შენსას და ამ კონცეფციას აყენებ?

ერთი სესიის ფარგლებში შესაძლებელი იყო და ახლაც შესაძლებელია სესიის მოდულში გამოვაცხადოთ ცვლადები, რომლებიც ცოცხალი და ხილული იქნება სესიის ფარგლებში სხვადასხვა ადგილიდან... რეალურად არის 4 მათგანი.
- სესიის მოდული;
- რეგულარული განაცხადის მოდული;
- მართული განაცხადის მოდული;
- გარე კავშირის მოდული.

და რა თქმა უნდა, თქვენ უნდა გახსოვდეთ კონტექსტი. სერვერის კონტექსტი პირდაპირ არ არის ხელმისაწვდომი კლიენტის მხრიდან და პირიქით.

ზოგადად, 1C არქიტექტურა ითვალისწინებს, რომ მონაცემთა გაცვლა გაგრძელდება:
- პროცედურების/ფუნქციების პარამეტრების/დაბრუნების საშუალებით;
- ეგრეთ წოდებული სესიის პარამეტრების საშუალებით (ისინი არ შეიძლება იყოს ობიექტები, თქვენ შეგიძლიათ რეალურად ნახოთ ეს პალიტრაში).

ცხრილი ფორმაზე... და ის დაკავშირებულია ობიექტის რომელიმე ცხრილთან (დამუშავება, მაგალითად)? თუ არა. თუ კი, მაშინ ის ასევე ხელმისაწვდომია სერვერზე (&AtServer) და იქ დაარედაქტირე....

დიახ, ValueTable არ არის ხელმისაწვდომი UV-ში კლიენტის მხარეს. ისე, 1C ასე გადაწყვიტა.

Მოდი! აქ მუშაობს Excel-ით, მუშაობს FSO-სთან და სხვა ყველაფერთან ერთად, მაგრამ აქ არ მუშაობს. დააფიქსირე შეცდომა და გაანალიზე....

მცდელობა
...
შენი ქმედებები
...
გამონაკლისი
str = DescriptionError();
მცდელობის დასასრული;

თანამედროვე აპარატურის შესაძლებლობებით, ეს საერთოდ არ არის არგუმენტი.

წმინდა შენი პირადი აზრი. არაფერი აქვს საერთო რეალობასთან. არავითარ შემთხვევაში. კიდევ ერთხელ ვიმეორებ, 1C მშვენივრად მუშაობს COM-თან. როგორც in-proc, ასევე out-proc-ით.

მიეცით კოდი, რომელსაც ატვირთავთ და მიმართეთ VK-ს.

სხვათა შორის, VK... შენს შემთხვევაში COMა თუ Native API?
თუ COM, მაშინ თქვენ დაარეგისტრირებთ მას როგორც... regsvr32-ის მეშვეობით... მაშინ როგორ "გადაწყვეტთ" ბიტის სიღრმის პრობლემას?

კითხვა: გარე კომპონენტის დაყენება


გთხოვთ მითხრათ როგორ დავაყენოთ გარე კომპონენტი. შემდეგი კოდის შესრულებისას ჩნდება შეცდომა. იპოვეთ NameDecl.dll განლაგებაში

SetExternalComponent-ის მცდელობა ("GeneralLayout.Layout"); გამონაკლისი EndTry;
შეცდომა: დანამატის ინსტალაცია ვერ მოხერხდა!

პასუხი: ()
ConnectExternalComponent ("GeneralLayout.Layout", "NameDecl", ExternalComponentType.Native) აბრუნებს FALSE,
New("AddIn.NameDecl.CNameDecl", Undefined) = (()): ტიპი არ არის განსაზღვრული (AddIn.NameDecl.NameDecl)

შეკითხვა: მშობლიური dll არ არის დაკავშირებული 1s 8.1-თან (fptrwin32_fz54_9_11_0_5549.dll)


გამარჯობა.
1C-მ განაახლა dll ონლაინ სალარო აპარატებისთვის atol fdd 1.05-ისთვის (შედის fptrwin32_fz54_9_11_0_5549.dll ტექნიკური დამუშავების პროცესში).
მე მაქვს ძველი 1C 8.1. 8.2-ისგან განსხვავებით, ის არ უჭერს მხარს გარე მოწყობილობებთან მუშაობას ისევე, როგორც 8.2, ასე რომ ჯერ უნდა დაარეგისტრიროთ dll Windows-ში და შემდეგ მხოლოდ დააკავშიროთ იგი 1C-ზე?

ProgID = "AddIn.IntegrationComponent.ATOL_KKT_1C83_V9"; LoadExternalComponent("C:\fptrwin32_fz54_9_11_0_5549.dll"); ConnectExternalComponent (ProgID); დრაივერი = ახალი (ProgID);

თუმცა, ძველი დამუშავება ეწერა "technology" com-ში და ახალი მშობლიური. შესაბამისად, რეგისტრაციისას, regsvr32 იძლევა შეცდომას:
მოდული ჩაიტვირთა, მაგრამ DllRegisterServer შესვლის წერტილი ვერ მოიძებნა. და გირჩევთ შეამოწმოთ, რომ ეს ფაილი არის სწორი dll ან OCX ფაილი.
ვის შეექმნა მსგავსი სიტუაცია, როგორ გამოხვედით? მესმის, რომ მსგავსი პრობლემა იქნება 7.7-ში.
კოდი 8.2:

Layout = GetLayout ("IntegrationComponent"); მისამართი = PlaceInTempStorage(Layout); ConnectExternalComponent(მისამართი, "IntegrationComponent", ExternalComponentType.Native); დრაივერი = ახალი ("AddIn.IntegrationComponent.ATOL_KKT_1C83_V9");

1C 8.2:
გარე კომპონენტის დაკავშირება (<Местоположение>, <Имя>, <Тип>)
1C 8.1:
გარე კომპონენტის დაკავშირება (<Идентификатор объекта>)
Პარამეტრები:
<Идентификатор объекта>(აუცილებელია)
ტიპი: სიმებიანი. გარე კომპონენტის ობიექტის ProgID (პროგრამული იდენტიფიკატორი). უნდა ემთხვეოდეს ინფორმაციას სისტემის სარეგისტრაციო მონაცემთა ბაზაში (რეგისტრი).
აღწერა:
აკავშირებს გარე კომპონენტის ობიექტებს 1C: Enterprise-თან.
მიუწვდომელია 1C:Enterprise სერვერზე. არ გამოიყენება გარე კავშირის მოდულში.
Შენიშვნა:
გარე კომპონენტები თავსებადია 1C:Enterprise 7.7 კომპონენტებთან.
მაგალითი:
მცდელობა
ConnectExternalComponent ("AddinObject.Scanner");
alert ("შტრიხკოდის სკანერის კომპონენტი ჩატვირთულია");
გამონაკლისი
alert ("შტრიხკოდის სკანერის კომპონენტი ჩატვირთული არ არის");
მცდელობების დასრულება

არის რაიმე გზა ამ dll-ის 8.1-თან დასაკავშირებლად თუ არა?

Გმადლობთ!

პასუხი:

მეც მქონდა ცოტა ხნის წინ ეს პრობლემა. შეუძლებელი გახდა 1-ის უფრო გვიანდელ ვერსიაზე გადაყვანა. dll, რომლითაც მუშაობს ეს კონფიგურაცია, უბრალოდ შეწყვიტა მუშაობა და 1c შეცდომით გავარდა.
პრობლემა მოგვარდა შემდეგი გზით:
შევქმენი ცარიელი მონაცემთა ბაზა 8.3, რომელშიც დავამუშავე კომპონენტის ინიციალიზაცია და შემდეგ 8.1-დან COM კავშირის საშუალებით შევედი ადრე შექმნილ მონაცემთა ბაზაში და იქ მოვახდინე კომპონენტის ინიციალიზაცია. შემდეგ, უკვე 8.1-ში, დავურეკე ამ კომპონენტის მეთოდებს.
რა თქმა უნდა, ეს ყავარჯენია, მაგრამ სხვა გამოსავალი ჯერ ვერ ვიპოვე (

კოდის მაგალითი 8.3:
Rem Driver Export;
ფუნქცია ConnectionComponentsCCP() ექსპორტი
მცდელობა

Layout = GetLayout ("IntegrationComponent");
მისამართი = PlaceInTempStorage(Layout);
ConnectExternalComponent(მისამართი, "IntegrationComponent", ExternalComponentType.Native);
დრაივერი = ახალი ("AddIn.IntegrationComponent.SMDrvFR1C20");
შედეგი = მართალია;

გამონაკლისი

შედეგი = მცდარი;

მცდელობის დასასრული;
დაბრუნების შედეგი
ბოლო ფუნქციები

კოდის მაგალითი 8.1

ფუნქცია CreateDriverObject(Driver) Export

შედეგი = მართალია;

მცდელობა

ConnectionString="File="""გზა მონაცემთა ბაზაში""";
ComObject= ახალი COMObject("V83.ComConnector");
Connect = ComObject.Connect(ConnectionString);

დამუშავება = Connect.Processing.ConnectingExternalComponent.Create();
ConnectionResult = Processing.ConnectingKKT კომპონენტები();
თუ შედეგი უკავშირდება მაშინ
Driver = Processing.Driver;
ბოლოს თუ;

გამონაკლისი
ვისაც ეს გაუკეთებია ან მსგავსი პრობლემა აქვს, გთხოვთ ამიხსნათ. მარტივი მაგალითითავად პრინციპი. როგორც ჩანს, ყველაფერი ნათელია გარე კომპონენტების კავშირთან დაკავშირებით.

// მნიშვნელობათა ცხრილის შევსების მაგალითი TK.Clear(); მოთხოვნა = ახალი მოთხოვნა; Query.Text = "არჩევა | ნომენკლატურა ბმული HOW ნომენკლატურა | FROM | Directory.Nomenclature AS Nomenclature"; QueryResult = Query.Execute(); Sampling = QueryResult.Select(); while Sampling.Next() Loop Str = TK.Add(); FillPropertyValues(Pr, Sampling); EndCycle;
შეგიძლიათ ამ მაგალითით აგიხსნათ კოდის რომელი ნაწილია ამოღებული. ლოგიკური იქნებოდა ნაწილის ამოღება მოთხოვნით, მაგრამ შემდეგ როგორ შევიდეთ მონაცემთა ბაზაში გარე კომპონენტიდან გარე კომპონენტიდან, პლატფორმის გვერდის ავლით? ტექსტი უაზროა. ან ამოიღეთ ცხრილის ნაწილის ფორმირება. გთხოვთ გაგვიზიაროთ თქვენი გამოცდილება ამასთან დაკავშირებით.

პასუხი:და რომ სიტყვა "შეუთავსებელი" ყოველთვის ნიშნავს სიტყვა "ცუდს"? დიახ, მეჩვენება, რომ თუ ჩემს სტილს ვუწოდებ "1C: ყველაზე ცუდი პროგრამირება ამ სკრიპტირების ძრავზე, რომელიც არსებობს ბუნებაში (თარგმნილია ლიტერატურულ ენაზე)!" და შემდეგ აუცილებლად იქნებიან ისინი, ვისაც სურს შეამოწმოს ეს მხეცი. და ეს კლასიკას ჰგავს: "პასტერნაკი არ წამიკითხავს, ​​მაგრამ სრულიად არ ვეთანხმები მას!" :)

შეკითხვა: გარე კომპონენტის დაკავშირება 1s 8.3.6-ში და Win8-ში


აუცილებელია vk_rs232.dll გარე კომპონენტის დაკავშირება თვითნაწერ კონფიგურაციასთან. როგორც რეგისტრირებულია regsvr32.exe-ის საშუალებით. "როგორც ჩანს", რადგან მე მივიღე შეტყობინება, რომ "კომპონენტი რეგისტრირებულია, მაგრამ რაღაც არასწორია firewall-თან." მესიჯის პირველ ნახევარზე დაყრდნობით ვწერ კოდს 1-ში
AfterConnection = New NotificationDescription("AfterConnectionVK",ThisForm); StartExternalComponentInstallation("C:\Controller\vk_rs232.dll"); StartConnectingExternalComponent(დაკავშირების შემდეგ,"C:\Controller\vk_rs232.dll","DLL_Scales");
და მე ვიღებ შეცდომას, რომ
"გარე კომპონენტის ინსტალაცია ვერ მოხერხდა! კლიენტის აპლიკაციის კომპონენტი, რომელსაც იყენებთ, შეიძლება არ იყოს!".

და ახლა არ მესმის
1. იქნებ კომპონენტი არ არის რეგისტრირებული რეესტრში - იქ როგორ შევამოწმო?
2. შეიძლება მისი "ვერსია" არ მუშაობს Win8-ზე, თუმცა მე მაქვს 32-ბიტიანი.
3. შესაძლოა 1s თავად არის ძალიან ახალი, ე.ი. შესაბამისად ამ dll-თან მუშაობა არ შეიძლება?
4. აბა, ბანალურია - რაღაცას არასწორად ვწერ.

პასუხი:და ამ ყველაფერმა მიმიყვანა შემდეგ პრობლემამდე. VneshComp დაინსტალირებულია, ახლა თქვენ უნდა დააკავშიროთ იგი. და აქ არის ორივე ვარიანტი.
ConnectExternalComponent ("C:\Controller\vk_rs232.dll","Scales")
ConnectExternalComponent ("GeneralLayout.Layout","Scales")

სინტაქსის ვარიანტი: სახელისა და ადგილმდებარეობის მიხედვით

Სინტაქსი:

გარე კომპონენტის დაკავშირება (<Местоположение>, <Имя>, <Тип>)
Პარამეტრები:

<Местоположение>(აუცილებელია)

ტიპი: სიმებიანი.
გარე კომპონენტის მდებარეობა.
მდებარეობის გამოყენება შესაძლებელია:
გზა გარე კომპონენტის ფაილამდე ფაილურ სისტემაში (არ არის ხელმისაწვდომი ვებ კლიენტზე), არა ZIP არქივი;
სრული სახელიგანლაგება, რომელიც ინახავს ორობით მონაცემებს ან ZIP არქივს;
გარე კომპონენტის URL, ორობითი მონაცემების ან ZIP არქივის სახით, GetNaviLink-ის მსგავსში.
<Имя>(აუცილებელია)

ტიპი: სიმებიანი.
ჩამრთველი გარე კომპონენტის სიმბოლური სახელი.
სახელი უნდა შეესაბამებოდეს ჩაშენებული ენის დასახელების კონვენციებს.
<Тип>(სურვილისამებრ)

ტიპი: გარე კომპონენტის ტიპი.
დასაკავშირებელი გარე კომპონენტის ტიპი.
არ გამოიყენება, თუ კომპონენტი შეფუთულია ZIP არქივში.
მეთოდის ვარიანტის აღწერა:

აკავშირებს Native და COM ტექნოლოგიით დამზადებულ კომპონენტებს.
კომპონენტი შეიძლება ინახებოდეს ინფო ბაზაში ან კონფიგურაციის განლაგებაში, როგორც ბინარული მონაცემები ან ZIP არქივში.
„Thin client“ და „Web Client“ გაშვების რეჟიმებისთვის, კომპონენტი წინასწარ უნდა იყოს დაინსტალირებული Install External Component მეთოდის გამოყენებით.
სინტაქსის ვარიანტი: ID-ით

Სინტაქსი:

გარე კომპონენტის დაკავშირება (<ИдентификаторОбъекта>)
Პარამეტრები:

<ИдентификаторОбъекта>(აუცილებელია)

ტიპი: სიმებიანი.
გარე კომპონენტის ობიექტის იდენტიფიკატორი MS Windows რეესტრის ProgID (პროგრამული იდენტიფიკატორი) სახით (მაგალითად: "AddIn.Scanner").
უნდა ემთხვეოდეს ინფორმაციას სისტემის სარეგისტრაციო მონაცემთა ბაზაში (რეგისტრი).
მეთოდის ვარიანტის აღწერა:

კომპონენტი უნდა განხორციელდეს COM ტექნოლოგიის გამოყენებით და დარეგისტრირდეს MS Windows-ის რეესტრში.
ეს კომპონენტები თავსებადია 1C:Enterprise 7.7 კომპონენტებთან.
ყურადღება! მეთოდის ვარიანტი არ მუშაობს სერვერზე და გარე კავშირში.
დაბრუნების ღირებულება:

ტიპი: ლოგიკური.
მართალია - კავშირი წარმატებული იყო.
აღწერა:

აკავშირებს გარე კომპონენტს 1C: Enterprise-თან.
გარე კომპონენტები შეიძლება ინახებოდეს ინფო ბაზაში ან კონფიგურაციის განლაგებაში ZIP არქივის სახით ან ბინარული მონაცემების სახით ან ფაილური სისტემის ფაილში.
თინ კლიენტზე და ვებ კლიენტზე მუშაობისას, კომპონენტი წინასწარ უნდა იყოს დაინსტალირებული.

ხელმისაწვდომობა:

თხელი კლიენტი, ვებ კლიენტი, სერვერი, გარე კავშირი.
Შენიშვნა:

გარე კომპონენტები შეიძლება განხორციელდეს Native API ან COM ტექნოლოგიის გამოყენებით. COM ტექნოლოგიით დამზადებული კომპონენტები თავსებადია 1C:Enterprise 7.7 კომპონენტებთან.
ვებ კლიენტს შეუძლია იმუშაოს მხოლოდ იმ კომპონენტებთან ინფო ბაზაში, რომლებიც შეფუთულია არქივში.
თხელი კლიენტს შეუძლია იმუშაოს არქივში შეფუთულ კომპონენტებთან და ფაილურ სისტემაში მდებარე კომპონენტებთან.
სქელ კლიენტს შეუძლია იმუშაოს კომპონენტების შენახვის ყველა ვარიანტთან. ამ შემთხვევაში, თუ კომპონენტი დაინსტალირებულია InstallExternalComponent მეთოდით, მაშინ გამოიყენება დაინსტალირებული კომპონენტი, ხოლო თუ ის არ არის დაინსტალირებული, მაშინ კომპონენტი მიიღება კავშირის დროს.
სერვერს შეუძლია ყველა კომპონენტთან მუშაობა. კომპონენტი ინახება სერვერის სესიისთვის.
მაგალითი:

თუ ConnectExternalComponent ("AddinObject.Scanner") მაშინ
alert ("შტრიხკოდის სკანერის კომპონენტი ჩატვირთულია");
წინააღმდეგ შემთხვევაში
alert ("შტრიხკოდის სკანერის კომპონენტი ჩატვირთული არ არის");
Დაასრულე თუ;

  • სახელმძღვანელო

შესავალი

ეს სტატია იძლევა იდეას, თუ როგორ მუშაობს გარე კომპონენტები 1C: Enterprise სისტემაში.
ნაჩვენები იქნება გარე კომპონენტის შემუშავების პროცესი 1C: Enterprise ვერსიის 8.2 სისტემისთვის, რომელიც მუშაობს Windows ოპერაციული სისტემის ქვეშ, სამუშაოს ფაილური ვერსიით. ეს ვარიანტი გამოიყენება მცირე ბიზნესისთვის განკუთვნილი გადაწყვეტილებების უმეტესობაში. VC განხორციელდება C++ პროგრამირების ენაზე.

გარე კომპონენტები "1C: Enterprise"

"1C: Enterprise" არის გაფართოებადი სისტემა. გაფართოებისთვის ფუნქციონირებასისტემა იყენებს გარე კომპონენტებს (VC). დეველოპერის თვალსაზრისით, VC არის გარე ობიექტი, რომელსაც აქვს თვისებები და მეთოდები და ასევე შეუძლია შექმნას მოვლენები 1C:Enterprise სისტემის მიერ დამუშავებისთვის.
გარე კომპონენტები შეიძლება გამოყენებულ იქნას ამოცანების კლასის გადასაჭრელად, რომელთა განხორციელება რთული ან თუნდაც შეუძლებელია 1C: Enterprise-ში ჩაშენებული პროგრამირების ენის გამოყენებით. კერძოდ, ეს კლასი მოიცავს ამოცანებს, რომლებიც მოითხოვს დაბალი დონის ურთიერთქმედებას ოპერაციულ სისტემასთან, მაგალითად, კონკრეტულ აპარატურასთან მუშაობისთვის.
1C: Enterprise სისტემა იყენებს ორ ტექნოლოგიას გარე კომპონენტების შესაქმნელად:
  • Native API-ის გამოყენებით
  • COM ტექნოლოგიის გამოყენებით
ამ ორ ტექნოლოგიას შორის შეზღუდვების გათვალისწინებით, განსხვავება უმნიშვნელოა, ამიტომ განვიხილავთ VK-ს განვითარებას Native API-ის გამოყენებით. საჭიროების შემთხვევაში, განხორციელებული განვითარება შეიძლება გამოყენებულ იქნას VC-ის განვითარებაზე COM ტექნოლოგიის გამოყენებით, ასევე, მცირე ცვლილებებით, გამოყენებული იქნას 1C: Enterprise სისტემაში სხვა ოპერაციული ვარიანტებით, გარდა ფაილის რეჟიმისა.
VK სტრუქტურა
1C:Enterprise სისტემის გარე კომპონენტი წარმოდგენილია როგორც DLL ბიბლიოთეკა. ბიბლიოთეკის კოდი აღწერს IComponentBase წარმოებულ კლასს. შექმნილ კლასში უნდა განისაზღვროს გარე კომპონენტის ფუნქციების განხორციელებაზე პასუხისმგებელი მეთოდები. გადაჭარბებული მეთოდები უფრო დეტალურად იქნება აღწერილი მოგვიანებით მასალის პრეზენტაციის დროს.

დემო VK-ის გაშვება

Დავალება:
  1. შეაგროვეთ გარე კომპონენტი, რომელიც მიეწოდება ITS გამოწერას და შექმნილია გარე კომპონენტის მექანიზმის ძირითადი შესაძლებლობების დემონსტრირებისთვის 1C-ში
  2. შეაერთეთ დემო კომპონენტი 1C კონფიგურაციასთან
  3. დარწმუნდით, რომ დეკლარირებული ფუნქციები სწორად მუშაობს
კომპილაცია
დემო VC განთავსებულია ITS სააბონენტო დისკზე "/VNCOMP82/example/NativeAPI" დირექტორიაში.
ჩვენ გამოვიყენებთ Microsoft Visual Studio 2008-ს დემო VK-ის ასაწყობად. ამ პროდუქტის სხვა ვერსიებს არ აქვს გამოყენებული Visual Studio პროექტის ფორმატის მხარდაჭერა.


გახსენით AddInNative პროექტი. პროექტის პარამეტრებში ჩვენ ვუკავშირდებით დირექტორიას პროექტის ასაშენებლად საჭირო სათაურის ფაილებთან. ნაგულისხმევად, ისინი განთავსებულია დირექტორიაში ITS დისკზე /VNCOMP82/შეიცავს.
აშენების შედეგი არის ფაილი /bind/AddInNative.dll. ეს არის შედგენილი ბიბლიოთეკა 1C კონფიგურაციასთან დასაკავშირებლად.
VK-ის დაკავშირება 1C კონფიგურაციასთან
მოდით შევქმნათ ცარიელი კონფიგურაცია 1C.
ქვემოთ მოცემულია მართული აპლიკაციის მოდულის კოდი.
var DemoComp; SystemStartup Procedure() ConnectExternalComponent("...\bind\AddInNative.dll", "DemoVK", ExternalComponentType.Native); DemoComp = New ("AddIn.DemoVK.AddInNativeExtension"); დასრულების პროცედურა
თუ 1C კონფიგურაციის დაწყებისას შეცდომა არ დაფიქსირდა, მაშინ VK წარმატებით იყო დაკავშირებული.
ზემოაღნიშნული კოდის შესრულების შედეგად, ობიექტი ჩნდება კონფიგურაციის გლობალურ ხილვადობაში. DemoComp An რომელსაც აქვს თვისებები და მეთოდები, რომლებიც განსაზღვრულია გარე ლობიოს კოდში.
ჩაშენებული ფუნქციონირების დემონსტრირება
მოდით შევამოწმოთ დემო VK-ის შესრულება. ამისათვის შევეცადოთ დავაყენოთ და წავიკითხოთ ზოგიერთი თვისება, მოვუწოდებთ VC მეთოდებს და ასევე მივიღოთ და დავამუშავოთ VC შეტყობინება.
ITS დისკზე მოწოდებულ დოკუმენტაციაში მითითებულია დემო VC-ის შემდეგი ფუნქციონირება:
  1. კომპონენტის ობიექტის მდგომარეობის მართვა
    მეთოდები: Ჩართვა, Გამორთვა
    Თვისებები: შედის
  2. ტაიმერის კონტროლი
    ყოველ წამს, კომპონენტი აგზავნის შეტყობინებას 1C: Enterprise სისტემა პარამეტრებით Კომპონენტი, ტაიმერიდა სისტემური საათის მრიცხველის სტრიქონი.
    მეთოდები: StartTimer, StopTimer
    Თვისებები: არის ტაიმერი
  3. მეთოდი ShowInStatusLine, რომელიც აჩვენებს სტატუსის ზოლში მეთოდზე გადაცემულ ტექსტს პარამეტრებად
  4. მეთოდი Სურათის ატვირთვა. ატვირთავს სურათს მითითებული ფაილიდან და გადასცემს მას 1C:Enterprise სისტემაში, როგორც ბინარული მონაცემები.
მოდით დავრწმუნდეთ, რომ ეს ფუნქციები მუშაობს. ამისათვის ჩვენ შევასრულებთ შემდეგ კოდს:
var DemoComp; SystemStart() პროცედურა ConnectExternalComponent(...); DemoComp = New ("AddIn.DemoVK.AddInNativeExtension"); DemoComp.Disable(); Notify (DemoComp. ჩართულია); DemoComp.Enable(); Notify (DemoComp. ჩართულია); DemoComp.StartTimer(); EndProcedure ProcedureExternalEventHandler(Source, Event, Data) Report(Source + " " + Event + " " + Data); დასრულების პროცედურა
კონფიგურაციის გაშვების შედეგი ნაჩვენებია სურათზე


მეთოდის ზარების შედეგები ნაჩვენებია "შეტყობინებების" პანელში DemoComp.Disable()და Demo.Comp.Enable(). იმავე პანელზე მომდევნო სტრიქონები შეიცავს VK-დან მიღებული შეტყობინებების დამუშავების შედეგებს - წყარო, ღონისძიებადა მონაცემებიშესაბამისად.

თვითნებური გარე კომპონენტის სახელი

ამოცანა: შეცვალეთ გარე კომპონენტის სახელი თვითნებურად.
წინა განყოფილებაში გამოყენებული იყო იდენტიფიკატორი AddInNative Extension, რომლის მნიშვნელობა არ იყო ახსნილი. Ამ შემთხვევაში AddInNative Extensionარის გაფართოების სახელი.
VC კოდი განსაზღვრავს მეთოდს RegisterExtensionAs, რომელიც უბრუნებს სახელს 1C: Enterprise სისტემას, რომელიც აუცილებელია VC-ის შემდგომი რეგისტრაციისთვის სისტემაში. რეკომენდებულია იდენტიფიკატორის მითითება, რომელიც გარკვეულწილად ავლენს გარე კომპონენტის არსს.
აქ არის მეთოდის სრული კოდი RegisterExtensionAsგაფართოების სახელით შეიცვალა:
bool CAddInNative::RegisterExtensionAs(WCHAR_T** wsExtensionName) ( wchar_t *wsExtension = L"SomeName"; int iActualSize = ::wcslen(wsExtension) + 1; WCHAR_T* if_Myll (mor) (mor) ((void**)wsExtensionName, iActualSize * sizeof(WCHAR_T))) ::convToShortWchar(wsExtensionName, wsExtension, iActualSize); დაბრუნება true; ) დაბრუნება false; )
ზემოთ მოყვანილ მაგალითში VK სახელი შეიცვალა ზოგიერთი სახელი. შემდეგ, VK-ს დაკავშირებისას, უნდა მიუთითოთ ახალი სახელი:
DemoComp = New ("AddIn.DemoVK.SomeName");

VK თვისებების სიის გაფართოება

Დავალება:
  1. VC თვისებების განხორციელების შესწავლა
  2. დაამატეთ სტრიქონის ტიპის წაკითხვა-ჩაწერის თვისება
  3. დაამატეთ წაკითხვის/ჩაწერის სტრიქონის ტიპის თვისება, რომელიც ინახავს თვისების ბოლო ნაკრების მონაცემთა ტიპს. ქონების ღირებულების დაყენებისას არანაირი ქმედება არ განხორციელდება

შექმნილი კომპონენტის თვისებების დასადგენად, დეველოპერმა უნდა განახორციელოს შემდეგი მეთოდები AddInNative.cpp ბიბლიოთეკის კოდში:
GetNProps
აბრუნებს თვისებების რაოდენობას ამ გაფართოებისთვის, 0 თუ არ არის თვისებები
FindProp
აბრუნებს იმ ქონების რიგით ნომერს, რომლის სახელწოდებაც არის გადაცემული პარამეტრებში
GetPropName
აბრუნებს ქონების სახელს მისი რიგითი და გავლილი ენის ID-ით
GetPropVal
აბრუნებს ქონების ღირებულებას მითითებული რიგითობით
SetPropVal
ადგენს ქონების ღირებულებას მითითებული რიგობით
IsPropReadable
აბრუნებს ქონების წაკითხვის დროშას მითითებული რიგითობით
IsPropWritable
აბრუნებს თვისების ჩაწერადობის დროშას მითითებული მიმდევრობის ნომრით


განვიხილოთ ზემოთ მოყვანილი კლასის მეთოდების განხორციელება CAddInNative.
დემო VC განსაზღვრავს 2 თვისებას: შედისდა არის ტაიმერი (ჩართულიადა IsTimerPresent).
ბიბლიოთეკის კოდის გლობალურ ასპექტში განსაზღვრულია ორი მასივი:
static wchar_t *g_PropNames = (L"IsEnabled", L"IsTimerPresent"); static wchar_t *g_PropNamesRu = (L"ჩართულია", L"არსებობს ტაიმერი");
რომლებიც ინახავს ქონების რუსულ და ინგლისურ სახელებს. სათაურის ფაილში AddInNative.hრიცხვი განისაზღვრება:
enum Props (ePropIsEnabled = 0, ePropIsTimerPresent, ePropLast // ყოველთვის ბოლო);
ePropIsEnabledდა ePropIsTimerPresent, შესაბამისად 0 და 1 მნიშვნელობებით, გამოიყენება თვისებების რიგითი რიცხვების ჩასანაცვლებლად მნიშვნელოვანი იდენტიფიკატორებით. ePropLast, რომელსაც აქვს 2 მნიშვნელობა, გამოიყენება თვისებების რაოდენობის მისაღებად (GetNProps მეთოდის გამოყენებით). ეს სახელები გამოიყენება მხოლოდ კომპონენტის კოდის შიგნით და მიუწვდომელია გარედან.
FindProp და GetPropName მეთოდები ეძებს მასივებს g_PropNamesდა g_PropNames.
ბიბლიოთეკის მოდულში ველების მნიშვნელობის შესანახად CAddInNative კლასს აქვს თვისებები, რომლებიც ინახავს კომპონენტის თვისებების მნიშვნელობას. მეთოდები GetPropValდა SetPropValშესაბამისად დააბრუნეთ და დააყენეთ ამ თვისებების მნიშვნელობა.
მეთოდები IsPropReadableდა IsPropWritableდა დაბრუნდი მართალიაან ყალბი, განცხადების ლოგიკის მიხედვით ქონების გავლილი რიგითობის მიხედვით.
მორგებული თვისების დასამატებლად:

  1. დაამატეთ მასივებში დასამატებელი ქონების სახელი g_PropNamesდა g_PropNames(ფაილი AddInNative.cpp)
  2. ჩამოთვლამდე რეკვიზიტები(ფაილი AddInNative.h) ადრე ePropLastდაამატეთ სახელი, რომელიც ცალსახად განსაზღვრავს დასამატებელ საკუთრებას
  3. მეხსიერების ორგანიზება ქონების მნიშვნელობების შესანახად (შექმენით კომპონენტის მოდულის ველები, რომლებიც ინახავს შესაბამის მნიშვნელობებს)
  4. შეიტანეთ ცვლილებები მეთოდებში GetPropValდა SetPropValწინა საფეხურზე გამოყოფილ მეხსიერებასთან ურთიერთობისთვის
  5. განაცხადის ლოგიკის შესაბამისად შეიტანეთ ცვლილებები მეთოდებში IsPropReadableდა IsPropWritable
1, 2, 5 პუნქტებს ახსნა არ სჭირდებათ. ამ ნაბიჯების განხორციელების დეტალები შეგიძლიათ იხილოთ სტატიის დანართში.
მოდით დავასახელოთ ტესტის თვისებები ტესტიდა აკრიფეთ Checkშესაბამისად. შემდეგ, 1-ლი პუნქტის შედეგად, ჩვენ გვაქვს:
static wchar_t *g_PropNames = (L"IsEnabled", L"IsTimerPresent", L"Test", L"TestType"); static wchar_t *g_PropNamesRu = (L"ჩართულია", L"HasTimer", L"Test", L"CheckType");
Ჩამონათვალი რეკვიზიტებიასე გამოიყურება:
enum Props (ePropIsEnabled = 0, ePropIsTimerPresent, ePropTest1, ePropTest2, ePropLast // ყოველთვის ბოლო);
კოდის საგრძნობლად გასამარტივებლად, ჩვენ გამოვიყენებთ STL C++-ს. კერძოდ, სიმებიანი მუშაობისთვის WCHAR, დააკავშირეთ ბიბლიოთეკა სტრიქონი.
მეთოდის მნიშვნელობის შესანახად ტესტი, განსაზღვრეთ კლასში CAddInNativeკერძო სფეროში:
სიმებიანი ტესტი1;
სტრიქონის პარამეტრების გადასატანად 1C:Enterprise-სა და გარე კომპონენტს შორის გამოიყენება 1C:Enterprise მეხსიერების მენეჯერი. მოდით უფრო ახლოს მივხედოთ მის შემოქმედებას. მეხსიერების გამოსაყოფად და გასათავისუფლებლად, შესაბამისად, გამოიყენეთ ფუნქციები AllocMemoryდა თავისუფალი მეხსიერება, განსაზღვრულია ფაილში MemoryManager.h. თუ საჭიროა სტრიქონის პარამეტრის გადაცემა 1C: Enterprise სისტემაში, გარე კომპონენტმა უნდა გამოყოს მისთვის მეხსიერება ფუნქციის გამოძახებით. AllocMemory. მისი პროტოტიპი ასე გამოიყურება:
ვირტუალური bool ADDIN_API AllocMemory (void** pMemory, ხელმოუწერელი გრძელი ulCountByte) = 0;
სადაც p მეხსიერება- მაჩვენებლის მისამართი, რომელშიც განთავსდება გამოყოფილი მეხსიერების მისამართი,
ulCountByte- გამოყოფილი მეხსიერების არეალის ზომა.
სტრიქონისთვის მეხსიერების გამოყოფის მაგალითი:
WCHAR_T *t1 = NULL, *ტესტი = L"TEST_STRING"; int iActualSize = wcslen(test1)+1; m_iMemory->AllocMemory((void**)&t1, iActualSize * sizeof(WCHAR_T)); ::convToShortWchar(&t1, test1, iActualSize);
სიმებიანი მონაცემთა ტიპებთან მუშაობის მოხერხებულობისთვის ჩვენ აღვწერთ ფუნქციას wstring_to_p. პარამეტრად იღებს wstring სტრიქონს. ფუნქციის შედეგი არის შევსებული სტრუქტურა tVariant. ფუნქციის კოდი:
bool CAddInNative::wstring_to_p(std::wstring str, tVariant* val) (char* t1; TV_VT(val) = VTYPE_PWSTR; m_iMemory-> AllocMemory((void**)&t1, (str.length()+1) sizeof(WCHAR_T));memcpy(t1, str.c_str(), (str.length()+1) * sizeof(WCHAR_T));val -> pstrVal = t1; val -> strLen = str.length(); დაუბრუნე სიმართლე ;)
შემდეგ მეთოდის switch განაცხადის შესაბამისი case განყოფილება GetPropValმიიღებს ფორმას:
case ePropTest1: wstring_to_p(test1, pvarPropVal); შესვენება;
მეთოდი SetPropVal:
შემთხვევა ePropTest1: if (TV_VT(varPropVal) != VTYPE_PWSTR) დააბრუნებს false; test1 = std::wstring((wchar_t*)(varPropVal -> pstrVal)); შესვენება;
მეორე თვისების განსახორციელებლად, ჩვენ განვსაზღვრავთ კლასის ველს CaddInNative
uint8_t ბოლო_ტიპი;
რომელშიც ჩვენ ვინახავთ ბოლო გადაცემული მნიშვნელობის ტიპს. ამისათვის დაამატეთ შემდეგი ბრძანება CaddInNative::SetPropVal მეთოდს:
ბოლო_ტიპი = TV_VT(varPropVal);
ახლა, როდესაც ვითხოვთ მეორე ქონების მნიშვნელობის წაკითხვას, ჩვენ დავაბრუნებთ მნიშვნელობას ბოლო_ტიპი, რასაც განსაზღვრული დავალება მოითხოვს.
მოდით შევამოწმოთ განხორციელებული ცვლილებების შესრულება.
ამისთვის წარმოგიდგენთ გარეგნობაკონფიგურაცია 1C ხედისთვის:
var DemoComp; SystemStartup Procedure() ConnectExternalComponent("...", "DemoVK", ExternalComponentType.Native); DemoComp = New ("AddIn.DemoVK.SomeName"); DemoComp.CheckType = 1; ანგარიში (სტრიქონი (DemoComp.TypeCheck)); DemoComp.Test = "ვასია"; ანგარიში (სტრიქონი (DemoComp.Test)); DemoComp.Test = "პეტია"; ანგარიში (სტრიქონი (DemoComp.Test)); ანგარიში (სტრიქონი (DemoComp.TypeCheck)); დასრულების პროცედურა
გაშვების შედეგად, ჩვენ ვიღებთ შეტყობინებების თანმიმდევრობას:
3
ვასია
პეტია
22

მეორე და მესამე შეტყობინებები არის წინა საფეხურზე მითითებული ქონების წაკითხვის შედეგი. პირველი და მეორე შეტყობინებები შეიცავს ქონების ბოლო ნაკრების ტიპის კოდს. 3 შეესაბამება მთელ რიცხვს, 22 - სტრიქონის მნიშვნელობას. ფაილში დგინდება ტიპებისა და მათი კოდების შესაბამისობა ტიპები.თ, რომელიც მდებარეობს ITS დისკზე.

მეთოდების ჩამონათვალის გაფართოება

Დავალება:
  1. გააფართოვეთ გარე კომპონენტის ფუნქციონირება შემდეგი ფუნქციებით:
  2. ისწავლეთ გარე კომპონენტების მეთოდების დანერგვა
  3. მეთოდი-ფუნქციის დამატება ფუნქცია 1, რომელიც პარამეტრად იღებს ორ სტრიქონს ("Parameter1" და "Parameter2"). შედეგად, ბრუნდება ფორმის სტრიქონი: „შეამოწმეთ. პარამეტრი 1, პარამეტრი 2"
  4. დარწმუნდით, რომ შეტანილი ცვლილებები მუშაობს.

შემქმნელი კომპონენტის მეთოდების დასადგენად, დეველოპერმა უნდა განახორციელოს შემდეგი მეთოდები AddInNative ბიბლიოთეკის კოდში:
GetNMethods, FindMethod, GetMethodName
შექმნილია, შესაბამისად, მეთოდების რაოდენობის მისაღებად, მეთოდის ნომრისა და სახელის მოსაძებნად. თვისებების შესაბამისი მეთოდების მსგავსი
GetNParams
აბრუნებს მეთოდის პარამეტრების რაოდენობას მითითებული მიმდევრობის ნომრით; თუ არ არსებობს მეთოდი ამ რიცხვით ან არ აქვს პარამეტრები, აბრუნებს 0-ს
GetParamDefValue
აბრუნებს მითითებული მეთოდის მითითებული პარამეტრის ნაგულისხმევ მნიშვნელობას
HasRetVal
აბრუნებს დროშას, რომელსაც აქვს მითითებული დაბრუნების მნიშვნელობის მქონე მეთოდს: true დაბრუნების მნიშვნელობის მქონე მეთოდებისთვის და ყალბიწინააღმდეგ შემთხვევაში
CallAsProc
ყალბი, ჩნდება გაშვების დროის შეცდომა და 1C: Enterprise მოდულის შესრულება ჩერდება. პარამეტრების მასივის მეხსიერება გამოყოფილი და გამოთავისუფლებულია 1C: Enterprise-ის მიერ.
CallAsFunc
ახორციელებს მეთოდს მითითებული რიგობით. თუ მეთოდი დაბრუნდება ყალბი, ჩნდება გაშვების დროის შეცდომა და 1C: Enterprise მოდულის შესრულება ჩერდება. პარამეტრების მასივის მეხსიერება გამოყოფილია 1C: Enterprise-ის მიერ. თუ დაბრუნებული მნიშვნელობა არის სტრიქონის ტიპის ან ორობითი მონაცემების, კომპონენტი ანაწილებს მეხსიერებას ფუნქციასთან ერთად AllocMemoryმეხსიერების მენეჯერი, იქ წერს მონაცემებს და ინახავს ამ მისამართს სტრუქტურის შესაბამის ველში. 1С: საწარმო გამოუშვებს ამ მეხსიერებას დარეკვით თავისუფალი მეხსიერება.
მეთოდების სრული აღწერა, მათ შორის პარამეტრების ჩამონათვალი, დეტალურად არის აღწერილი ITS დისკზე მოწოდებულ დოკუმენტაციაში.
განვიხილოთ ზემოთ აღწერილი მეთოდების განხორციელება.
კომპონენტის კოდში ორი მასივია განსაზღვრული:
static wchar_t *g_MethodNames = (L"Enable", L"Disable", L"ShowInStatusLine", L"StartTimer", L"StopTimer", L"LoadPicture"); static wchar_t *g_MethodNamesRu = (L"Enable", L"Disable", L"ShowInStatusLine", L"StartTimer", L"StopTimer", L"LoadImage");
და რიცხვი:
enum მეთოდები (eMethEnable = 0, eMethDisable, eMethShowInStatusLine, eMethStartTimer, eMethStopTimer, eMethLoadPicture, eMethLast // ყოველთვის ბოლო );
ისინი გამოიყენება ფუნქციებში GetNMethods, FindMethodდა GetMethodNameთვისებების აღწერის ანალოგიით.
მეთოდები GetNParams, GetParamDefValue, HasRetValჩამრთველის განხორციელება, გავლილი პარამეტრებისა და აპლიკაციის ლოგიკის მიხედვით, დააბრუნებს საჭირო მნიშვნელობას. მეთოდი HasRetValმის კოდში არის მხოლოდ მეთოდების სია, რომლებსაც შეუძლიათ შედეგის დაბრუნება. მათთვის ის ბრუნდება მართალია. ფოლადის ყველა მეთოდისთვის ბრუნდება ყალბი.
მეთოდები CallAsProcდა CallAsFuncშეიცავს პირდაპირ შესრულებადი მეთოდის კოდს.
მეთოდის დასამატებლად, რომლის გამოძახება შესაძლებელია მხოლოდ ფუნქციის სახით, თქვენ უნდა განახორციელოთ შემდეგი ცვლილებები გარე კომპონენტის საწყის კოდში:
  1. დაამატეთ მეთოდის სახელი მასივებს g_MethodNamesდა g_MethodNames(ფაილი AddInNative.cpp)
  2. დაამატეთ მეთოდის მნიშვნელოვანი იდენტიფიკატორი Methods enum-ში (ფაილი AddInNative.h)
  3. შეიტანეთ ცვლილებები ფუნქციის კოდში GetNParamsპროგრამის ლოგიკის მიხედვით
  4. საჭიროების შემთხვევაში, შეიტანეთ ცვლილებები მეთოდის კოდში GetParamDefValueთუ გსურთ გამოიყენოთ მეთოდის პარამეტრების ნაგულისხმევი მნიშვნელობები.
  5. შეიტანეთ ცვლილებები ფუნქციაში HasRetVal
  6. შეიტანეთ ცვლილებები ფუნქციების ლოგიკაში CallAsProcან CallAsFuncმეთოდის უშუალოდ შესრულებადი კოდის იქ განთავსებით
მოვიტანოთ მასივები g_MethodNamesდა g_MethodNames, ასევე ჩამოთვლა მეთოდებიხედისკენ:
static wchar_t *g_MethodNames = (L"Enable", L"Disable", L"ShowInStatusLine", L"StartTimer", L"StopTimer", L"LoadPicture", L"Test"); static wchar_t *g_MethodNamesRu = (L"Enable", L"Disable", L"ShowInStatusLine", L"StartTimer", L"StopTimer", L"LoadImage", L"Test");

Enum Methods (eMethEnable = 0, eMethDisable, eMethShowInStatusLine, eMethStartTimer, eMethStopTimer, eMethLoadPicture, eMethTest, eMethLast // ყოველთვის ბოლო );
მოდით შევცვალოთ ფუნქცია GetNPropsასე რომ დააბრუნებს "ტესტის" მეთოდის პარამეტრების რაოდენობას:
long CAddInNative::GetNParams(const long lMethodNum) ( switch(lMethodNum) ( case eMethShowInStatusLine: return 1; case eMethLoadPicture: return 1; case eMethTest: return 2; default: return 0; ) return 0; )
მოდით შევიტანოთ ცვლილებები ფუნქციაში:
bool caddinnative :: getParamDefValue (const long lmethodnum, const long lparamnum, tvariant *pvarparamdefvalue) (tv_vt (pvarparamdefvalue) = vtype_empty; შეცვლა (lmethodnum) (Case emethenable: case emethdidisable : case / არ არის პარამეტრის მნიშვნელობები ნაგულისხმევი შესვენებით; ნაგულისხმევი: return false; ) return false;)
დამატებული ხაზის წყალობით
საქმე eMethTest:
ერთი ან მეტი არგუმენტის არარსებობის შემთხვევაში, შესაბამის პარამეტრებს ექნება ცარიელი მნიშვნელობა ( VTYPE_EMPTY). თუ თქვენ გჭირდებათ პარამეტრის ნაგულისხმევი მნიშვნელობა, ის უნდა მიუთითოთ განყოფილებაში eMethTestფუნქციის შეცვლის განცხადება CAddInNative::GetParamDefValue.
ვინაიდან „ტესტის“ მეთოდს შეუძლია დააბრუნოს მნიშვნელობა, თქვენ უნდა შეიტანოთ ცვლილებები ფუნქციის კოდში HasRetVal:
bool CAddInNative::HasRetVal(const long lMethodNum) ( switch(lMethodNum) ( case eMethLoadPicture: case eMethTest: return true; ნაგულისხმევი: return false; ) return false; )
და დაამატეთ მეთოდის შესრულებადი კოდი ფუნქციას CallAsFunc:
bool CAddInNative::CallAsFunc(const long lMethodNum, tVariant* pvarRetValue, tVariant* paParams, const long lSizeArray) ( ... std::wstring s1, s2; switch(lMethodNum) (შემთხვევა eMethT case: ...eMethLoad;P; თუ (!lSizeArray || !paParams) დააბრუნებს false; s1 = (paParams) -> pwstrVal; s2 = (paParams+1) -> pwstrVal; wstring_to_p(std::wstring(s1+s2), pvarRetValue); ret = true ; შესვენება; ) დაბრუნება ret;)
მოდით შევადგინოთ კომპონენტი და მივიყვანოთ კონფიგურაციის კოდი ფორმაში:
var DemoComp; SystemStartup Procedure() ConnectExternalComponent("...", "DemoVK", ExternalComponentType.Native); DemoComp = New ("AddIn.DemoVK.SomeName"); lane = DemoComp.Test ("Hi, ", "World!"); Notify(trans); დასრულების პროცედურა
კონფიგურაციის დაწყების შემდეგ, ჩვენ მივიღებთ შეტყობინებას: "გამარჯობა, მსოფლიო!", რაც მიუთითებს იმაზე, რომ მეთოდი წარმატებით მუშაობდა.

ტაიმერი

Დავალება:
  1. შეისწავლეთ ტაიმერის განხორციელება დემო VK-ში
  2. შეცვალეთ "StartTimer" მეთოდი პარამეტრებში ტაიმერის ინტერვალის (მილიწამებში) გადაცემის შესაძლებლობის დამატებით.
  3. დარწმუნდით, რომ შეტანილი ცვლილებები მუშაობს.

WinAPI-ში, დროსთან მუშაობისთვის, შეგიძლიათ გამოიყენოთ შეტყობინება WM_TIMER. ეს შეტყობინება გაიგზავნება თქვენს პროგრამაში იმ დროის ინტერვალში, რომელიც თქვენ მიუთითეთ ტაიმერის შექმნისას.
ტაიმერის შესაქმნელად გამოიყენეთ ფუნქცია SetTimer:
UINT SetTimer(HWND hWnd, // ფანჯრის სახელური UINT nIDevent, // ტაიმერის იდენტიფიკატორი (ნომერი) UINT nElapse, // დაყოვნება TIMERPROC lpTimerFunc); // ფუნქციის მაჩვენებელი
ოპერაციული სისტემა გამოგიგზავნით შეტყობინებას WM_TIMERპროგრამას არგუმენტში მითითებული ინტერვალით გასვლა(მილიწამებში). ბოლო პარამეტრში შეგიძლიათ მიუთითოთ ფუნქცია, რომელიც შესრულდება ტაიმერის გაშვების ყოველ ჯერზე. ამ ფუნქციის სათაური ასე უნდა გამოიყურებოდეს (სახელი შეიძლება იყოს ნებისმიერი):
void __stdcall TimerProc (HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime)
განვიხილოთ ტაიმერის განხორციელება დემო VK-ში.
ვინაიდან ჩვენ განვიხილავთ Windows ოჯახის ოპერაციული სისტემისთვის გარე კომპონენტის შემუშავების პროცესს, ჩვენ არ განვიხილავთ ტაიმერის დანერგვას სხვა ოპერატიული სისტემა. GNU/Linux OS-ისთვის, კერძოდ, იმპლემენტაცია განსხვავდება ფუნქციის სინტაქსით SetTimerდა TimerProc.
მეთოდი ეწოდება შესრულებად კოდში SetTimer, რომელსაც გადაეცემა ფუნქცია MyTimerProc:
m_uiTimer = ::SetTimer(NULL,0,100,(TIMERPROC)MyTimerProc);
შექმნილი ტაიმერის ID მოთავსებულია ცვლადში m_uiTimerრათა მოგვიანებით გამორთოთ.
ფუნქცია MyTimerProcშემდეგნაირად:
ბათილი გამოძახება MyTimerProc(HWND hwnd, // ფანჯრის სახელური ტაიმერის შეტყობინებებისთვის UINT uMsg, // WM_TIMER შეტყობინება UINT idEvent, // ტაიმერის იდენტიფიკატორი DWORD dwTime // სისტემის მიმდინარე დრო) ( if (!pAsyncEvent) *who =wchart "ComponentNative", *what = L"Timer"; wchar_t *wstime = new wchar_t; if (wstime) ( wmemset(wstime, 0, TIME_LEN); ::_ultow(dwTime, wstime, 10); pAsyncEvent->ExternalEvent(who , რა, wstime); წაშალე wstime; ))
ფუნქციის არსი იმაში მდგომარეობს, რომ მეთოდი ე.წ გარე ღონისძიება, რომელიც აგზავნის შეტყობინებას 1C: Enterprise სისტემაში.
მეთოდის ფუნქციონირების გაფართოება StartTimerმოდით გავაკეთოთ შემდეგი:
მეთოდის კოდის შეცვლა GetNParamsისე რომ მეთოდისთვისაა eMethStartTimerდაბრუნებული მნიშვნელობა 1:
საქმე eMethStartTimer: დაბრუნება 1;
აქ არის მეთოდის კოდი CallAsProcხედისკენ:
შემთხვევა eMethStartTimer: if (!lSizeArray || TV_VT(paParams) != VTYPE_I4 || TV_I4(paParams)<= 0) return false; pAsyncEvent = m_iConnect; #ifndef __linux__ m_uiTimer = ::SetTimer(NULL,0,TV_I4(paParams),(TIMERPROC)MyTimerProc); #else // код для GNU/Linux #endif break;
ახლა მოდით შევამოწმოთ ფუნქციონირება. ამისათვის, კონფიგურაციის მართული აპლიკაციის მოდულში ჩავწერთ კოდს:
var DemoComp; SystemStartup Procedure() ConnectExternalComponent("...", "DemoVK", ExternalComponentType.Native); DemoComp = New ("AddIn.DemoVK.SomeName"); DemoComp.StartTimer(2000); დასრულების პროცედურა
კონფიგურაციის დაწყების შემდეგ პროგრამა მიიღებს შეტყობინებებს 2 წამის ინტერვალით, რაც მიუთითებს ტაიმერის სწორ მუშაობაზე.

ურთიერთქმედება 1C: Enterprise სისტემასთან

გარე კომპონენტსა და 1C:Enterprise სისტემას შორის ურთიერთქმედებისთვის, ფაილში აღწერილი IAddInDefBase კლასის მეთოდები AddInDefBase.h. ჩვენ ჩამოვთვლით ყველაზე ხშირად გამოყენებულ:
შეცდომის შეტყობინებების გენერირება
ვირტუალური bool ADDIN_API AddError (ხელმოუწერელი მოკლე wcode, const WCHAR_T* წყარო, const WCHAR_T* descr, long scode)
wcode, კოდი- შეცდომის კოდები (შეცდომის კოდების სია აღწერილობით შეგიძლიათ იხილოთ ITS დისკზე)
წყარო- შეცდომის წყარო
აღწერ- შეცდომის აღწერა
შეტყობინების გაგზავნა 1C: Enterprise სისტემაში
ვირტუალური bool ADDIN_API ExternalEvent(WCHAR_T* wszSource, WCHAR_T* wszMessage, WCHAR_T* wszData) = 0;
wszწყარო- შეტყობინების წყარო
wszმესიჯი- შეტყობინების ტექსტი
wszData- გადაცემული მონაცემები
შეტყობინების ჩაჭრა ხორციელდება პროცედურა HandlingExternalEvent
გარე კომპონენტის რეგისტრაცია 1C:Enterprise სისტემაში
ვირტუალური bool ADDIN_API RegisterProfileAs(WCHAR_T* wszProfileName)
wszProfileName- კომპონენტის სახელი.
ეს მეთოდები საკმარისია VK-ისა და 1C-ის სრული ურთიერთქმედებისთვის. 1C:Enterprise სისტემიდან გარე კომპონენტის მიერ მონაცემების მისაღებად და პირიქით, გარე კომპონენტი აგზავნის სპეციალურ შეტყობინებას, რომელიც, თავის მხრივ, იჭრება 1C სისტემის მიერ და, საჭიროების შემთხვევაში, მოუწოდებს გარე კომპონენტის მეთოდებს გაგზავნისთვის. უკან მონაცემები.

tVariant მონაცემთა ტიპი

გარე კომპონენტსა და 1C:Enterprise სისტემას შორის მონაცემთა გაცვლისას გამოიყენება tVariant მონაცემთა ტიპი. ის აღწერილია Types.h ფაილში, რომელიც შეგიძლიათ იხილოთ ITS დისკზე:
struct _tvariant (_anonymous_union Union (int8_t i8val; int16_t Shortval; int32_t lval; intval; insigned int uintval; int64_t llval; uint8_t ui8val; uint16_t ushortval; bVal; char chVal; wchar_t wchVal; DATE თარიღი; IID IDVal; struct _tVariant *pvarVal; struct tm tmVal; _ANONYMOUS_STRUCT struct ( void* pInterfaceVal; IID InterfaceID; ) __VARIANT_NAMEY_2; /ბაიტების რაოდენობა ) __VARIANT_NAME_3/*str*/; _ANONYMOUS_STRUCT struct ( WCHAR_T* pwstrVal; uint32_t wstrLen; //სიმბოლოების რაოდენობა ) __VARIANT_NAME_4/*wstr*/; ) __VARIANT_STRUCT განზომილება 2-რეიტი; pvarVal-ში TYPEVAR vt; );
ტიპი tVariantარის სტრუქტურა, რომელიც მოიცავს:
  • ნარევი (კავშირი), რომელიც განკუთვნილია უშუალოდ მონაცემთა შესანახად
  • მონაცემთა ტიპის იდენტიფიკატორი
ზოგადად, ტიპის ცვლადებთან მუშაობა tVariantხდება შემდეგი ალგორითმის მიხედვით:
  1. ამჟამად ცვლადში შენახული მონაცემების ტიპის განსაზღვრა
  2. წვდომა ნარევის შესაბამის ველზე, მონაცემების პირდაპირი წვდომისთვის
ტიპის გამოყენება tVariantმნიშვნელოვნად ამარტივებს 1C: Enterprise სისტემისა და გარე კომპონენტის ურთიერთქმედებას

განაცხადი

დირექტორია "მაგალითები" შეიცავს სტატიის მაგალითებს
მაგალითები/1 - გაუშვით დემო კომპონენტი
მაგალითები/2 - ქონების სიის გაფართოების დემო ვერსია
მაგალითები/3 - მეთოდების სიის გაფართოების დემონსტრირება
თითოეული დირექტორია შეიცავს VS 2008 პროექტს და წინასწარ აშენებულ 1C კონფიგურაციას.

ხშირად, პროგრამისტებს პრობლემები აქვთ გარე კომპონენტების (მაგალითად, კომერციული აღჭურვილობის დრაივერების) დაკავშირებისას, როდესაც მომხმარებლები მუშაობენ 1C-თან ტერმინალის საშუალებით სერვერთან დაკავშირების გზით.

ამავდროულად, მომხმარებლები ხედავენ, მაგალითად, სტატიის ანონსში წარმოდგენილ სურათს.

ადგილობრივი კომპიუტერებიდან მუშაობისას, გარე კომპონენტების დაკავშირების პრობლემა არ არის.

რასთან არის დაკავშირებული? ეს იმიტომ ხდება, რომ როდესაც მომხმარებლები მუშაობენ ტერმინალ სერვერზე, მათ აქვთ ნაკლები უფლებები, ვიდრე ლოკალურ კომპიუტერზე მუშაობისას.

ამის შემოწმება მარტივია, თუ შეხვალთ ტერმინალის სერვერზე ადმინისტრაციული უფლებების მქონე ანგარიშის ქვეშ.

ამ განსხვავების მიზეზი არის ის, რომ 1C არ შეუძლია დაარეგისტრიროს გარე კომპონენტი რეესტრში, როდესაც მომხმარებელი მუშაობს ტერმინალში ნორმალური უფლებებით, რადგან ჩვეულებრივ მომხმარებელს არ აქვს ჩაწერის უფლება სისტემის რეესტრის ფილიალში HKEY_CLASSES_ROOT.

ტერმინალში გარე კომპონენტების დაკავშირების თემაზე პუბლიკაციებში შემოთავაზებულია ამ პრობლემის გადაჭრის სხვადასხვა მეთოდი.

მაგალითად, ესენი:

1. გაუშვით 1C პირველად ადმინისტრაციული უფლებებით.

ეს ვარიანტი ყოველთვის არ მუშაობს. ქვემოთ აგიხსნით რატომ.

2. მიეცით ტერმინალის რიგით მომხმარებლებს სისტემის რეესტრის ფილიალში ჩაწერის უფლება HKEY_CLASSES_ROOT.

არასაკმარისად "მოწინავე" მომხმარებლებმა არ უნდა გააკეთონ ეს, წინააღმდეგ შემთხვევაში შეიძლება პრობლემები იყოს.

3. სხვადასხვა „გაჯეტების“ გამოყენებით დაარეგისტრირეთ VK სრული უფლებების მქონე მომხმარებლის სახელით.

არც ჭამა არის კარგი.

მაშ, რა არის საუკეთესო გზა ამ სიტუაციიდან გამოსასვლელად?

მე გთავაზობთ ამ პრობლემის ჩემს გადაწყვეტას. ჩემი აზრით - მარტივი და ლამაზი, ადრე არ იყო შემოთავაზებული ინფოსტარტზე.

ამ პრობლემის გამოკვლევისას მაინტერესებდა - რატომ ცდილობს 1C დაარეგისტრიროს VK ახალ გზაზე? ყოველივე ამის შემდეგ, ის უკვე რეგისტრირებულია სისტემაში.

საქმე ის იყო, რომ ტიპიურ 1C კონფიგურაციებში (მაგალითად, "ვაჭრობის მენეჯმენტი") გამოიყენება გლობალური კონტექსტის მეთოდის შემდეგი სინტაქსი. ConnectExternalComponent() :

ConnectExternalComponent ("Reference.ConnectedEquipment.Layout.DriverATOLShircodeScanner", "ATOLScanner");

როგორც ხედავთ, VK დრაივერი დაკავშირებულია "დაკავშირებული აღჭურვილობის" დირექტორიაში "DriverATOLScannerBarcode" განლაგებიდან.

მერე რა ხდება?

1C ინახავს კომპონენტს მომხმარებლის დროებით საქაღალდეში, მაგალითად "C:\Documents and Settings\User\Local Settings\Temp\1032\v8_4_12.tmp"

და ცდილობს მის რეგისტრაციას HKEY_CLASSES_ROOT რეესტრის ფილიალში ამ გზაზე.

ტერმინალზე ჩვეულებრივ მომხმარებლებს არ აქვთ უფლება შეცვალონ ეს რეესტრის ფილიალი, ამიტომ კომპონენტი მათთვის არ არის დაკავშირებული.

ახლა იმის შესახებ, თუ როგორ გამოვიდეთ ამ სიტუაციიდან.

გლობალური კონტექსტის მეთოდი ConnectExternalComponent()-ს აქვს რამდენიმე სინტაქსის ვარიანტი. ეს არის ის, რასაც ჩვენ გამოვიყენებთ.

ასე რომ, ეტაპობრივად:

1. დაარეგისტრირეთ გარე კომპონენტი regsvr32.exe პროგრამის გამოყენებით ტერმინალის სერვერზე C:\WINDOWS\SYSTEM32 საქაღალდეში 32-ბიტიანი OS-ისთვის ან საქაღალდეში C:\WINDOWS\SYSWOW64 64-ბიტიანი ოპერაციული სისტემისთვის.

2. გამოიყენეთ ConnectExternalComponent() მეთოდისთვის ორი დამატებითი სინტაქსიდან ერთ-ერთი:

ვარიანტი 1:

ConnectExternalComponent ("C:\WINDOWS\SysWOW64\Scaner1C.dll", "ATOLScanner", ExternalComponentType.COM);

DriverObject = ახალი ("AddIn.ATOLScanner.Scanner45");

ვარიანტი 2:

ProgID = "AddIn.Scanner45";

გარე კომპონენტის (ProgID) დაკავშირება;

DriverObject = New(ProgID);

ჩემი აზრით, ვარიანტი #2 სასურველია.

ამავდროულად, 1C არ ცდილობს VC-ის ხელახლა დარეგისტრირებას რეესტრში ახალი გზის გასწვრივ და, ამრიგად, ყველა პრობლემა მოგვარებულია.

აბა, სულ ესაა. წარმატებები სამსახურში!

მაგალითად, შეუძლებელი იქნება კომპონენტის გადაწერა, თუ თქვენ არ ხართ მისი ავტორი და უბრალოდ არ არსებობს წყაროს კოდები. ან თუ Native API ტექნოლოგიით მხარდაჭერილი უმარტივესი ტიპები (რიცხვი, სტრიქონი, ლოგიკური, თარიღი) საკმარისი არ არის მისი მუშაობისთვის.

ფაილების ბაზასთან მუშაობისას განსაკუთრებული პრობლემები არ არის. დაგეგმილი დავალება იწოდება ჩვეულებრივი მომხმარებლის ფონურ პროცესში. ამიტომ, კლიენტის ზარები მისთვის ხელმისაწვდომია. არ არსებობს კლიენტის კონტექსტი სერვერის მონაცემთა ბაზაში, როდესაც დაგეგმილი დავალება იწყება, ამიტომ ზარი ConnectExternalComponent()მიუწვდომელია.

ამ შემთხვევაში, თქვენ შეგიძლიათ დარეკოთ კომპონენტი კლიენტზე. ამისათვის საკმარისია სერვერზე დაგეგმილი ამოცანიდან კიდევ ერთი 1C სესიის გაშვება, რომელშიც კლიენტზე საჭირო მოქმედებები შეასრულეთ. კარგად, არ დაგავიწყდეთ გაშვებული სესიის დასრულება მოგვიანებით.

ვთქვათ, რომ ჩვენს დაგეგმილ ამოცანაში, ჩვენ ვქმნით და ვინახავთ ანგარიშს, რომელიც იყენებს გარე COM კომპონენტს NameDeclension.dll სრული სახელის უარყოფისთვის. ფაილის ბაზაზე, ასეთი დაგეგმილი დავალება იმუშავებს სწორად, მაგრამ ის არ იმუშავებს სერვერის კომპონენტზე.

პრობლემის გადასაჭრელად დავამატოთ პროცედურა დაგეგმილ დავალების მოდულს, რომელიც დაიწყებს სხვა სესიას სერვერის რეჟიმში და მასში შეასრულებს კლიენტზე ანგარიშის გენერირების ზარს გარე დამუშავებიდან.

#If Client then Procedure ExecuteFormationAndSavingReport() Export If ConnectExternalComponent("CommonLayout.NAMEDECL","Cl",ExternalComponentType.COM) then Component = New ("AddIn.Cl.NameDeclension"); //აქ არის ანგარიშის გენერირებისა და შენახვის კოდი ElseJoinRegisterLog("RegistTask", LevelJoinLog.Error, "ვერ მოხერხდა კლიენტზე გარე კომპონენტის დაკავშირება"); Დაასრულე თუ; პროცედურის დასასრული #Otherwise Procedure ExecuteFormationAndSavingReport() Export ExecuteOperationOnClient("RegularTasks.ExecuteFormationAndSavingReport()"); EndProcedure Procedure PerformOperationOnClient(ParameterToExecute) ExportUserName = ""; მომხმარებლის პაროლი = ""; PathToExternalProcessing = "c:/temp/Autostart.epf"; ციტატა = """"; DirectoryBIN = DirectoryProgram(); PathToConfiguration = InfoBase ConnectionString(); ConfigurationPath = StrReplace(ConfigurationPath, Quote, Quote + Quote); StartString = ციტატა + Bin დირექტორია + "1cv8.exe" + ციტატა + " ENTERPRISE" + " /IBConnectionString " + ციტატა + ConfigurationPath + ციტატა + " /N " + ციტატა + მომხმარებლის სახელი + ციტატა + " /P " + ციტატა + მომხმარებლის პაროლი + ციტატა + " /Execute " + ციტატა + PathToExternalProcessing + ციტატა + " /C " + ციტატა + ParameterToExecute + ციტატა; StartApplication(StartString); დასრულების პროცედურა #EndIf

გარე დამუშავების კოდი, რომელიც უბრალოდ გამოიწვევს კლიენტის კონტექსტს დაბეჭდოს საჭირო ანგარიში დაგეგმილი სამუშაოების მოდულიდან და დაასრულოს სესია ანგარიშის გენერირების შემდეგ.

შესრულების მცდელობა (StartupParameter); გამონაკლისი EndTry; ShutdownSystem(False);

გადაწყვეტის მოხერხებულობა იმაში მდგომარეობს, რომ დაგეგმილი ამოცანების დაყენებისას არ აქვს მნიშვნელობა, რა რეჟიმში დაიწყება დავალება. თუ მონაცემთა ბაზა არის ფაილური, მაშინ საჭირო პროცედურა დაუყოვნებლივ დაიწყება. თუ მონაცემთა ბაზა სერვერის მხარესაა და არ არის კლიენტის კონტექსტი გაშვებისას, მაშინ ახალი სესიის ინიციალიზაცია მოხდება და პროცედურა სწორად იმუშავებს კლიენტის კონტექსტში.

კოდი ტიპიური აპლიკაციისთვის. თეორიულად, ის სრულიად ანალოგიურად იმუშავებს მართულში.

p.s.ასევე, ეს მიდგომა შეიძლება გამოყენებულ იქნას ნებისმიერი კლიენტის პროცედურის შესასრულებლად დაგეგმილ სამუშაოებში.

ᲖᲐᲠᲘ

არიან ისეთებიც, ვინც ამ ამბებს შენამდე კითხულობს.
გამოიწერეთ უახლესი სტატიების მისაღებად.
ელფოსტა
სახელი
გვარი
როგორ გინდა წაიკითხო ზარი
არ არის სპამი